     1                                  ; ****************************************************************************
     2                                  ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.3
     3                                  ; ----------------------------------------------------------------------------
     4                                  ; Last Update: 30/11/2020
     5                                  ; ----------------------------------------------------------------------------
     6                                  ; Beginning: 04/01/2016
     7                                  ; ----------------------------------------------------------------------------
     8                                  ; Assembler: NASM version 2.15 (trdos386.s)
     9                                  ; ----------------------------------------------------------------------------
    10                                  ; Turkish Rational DOS
    11                                  ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                                  ;
    13                                  ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                                  ; unix386.s (03/01/2016)
    15                                  ;
    16                                  ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    17                                  ; TRDOS2.ASM (09/11/2011)
    18                                  ; 
    19                                  ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    20                                  ; ****************************************************************************
    21                                  ; nasm trdos386.s -l trdos386.txt -o TRDOS386.SYS
    22                                  
    23                                  
    24                                  KLOAD	equ 10000h ; Kernel loading address
    25                                  	; NOTE: Retro UNIX 8086 v1 /boot code loads kernel at 1000h:0000h 
    26                                  KCODE	equ 08h	; Code segment descriptor (ring 0)
    27                                  KDATA	equ 10h	; Data segment descriptor (ring 0)
    28                                  ; 19/03/2015
    29                                  UCODE	equ 1Bh ; 18h + 3h  (ring 3)
    30                                  UDATA	equ 23h ; 20h + 3h  (ring 3)
    31                                  ; 24/03/2015
    32                                  TSS	equ 28h	; Task state segment descriptor (ring 0)
    33                                  ; 19/03/2015
    34                                  CORE	equ 400000h  ; Start of USER's virtual/linear address space 
    35                                  		     ; (at the end of the 1st 4MB)
    36                                  ECORE	equ 0FFC00000h ; End of USER's virtual address space (4GB - 4MB)
    37                                  		     ; ULIMIT = (ECORE/4096) - 1 = 0FFBFFh (in GDT)
    38                                  
    39                                  ;; 27/12/2013
    40                                  ;KEND    equ KLOAD + 65536 ; (28/12/2013) (end of kernel space)
    41                                  ; 04/07/2016
    42                                  KEND    equ KERNELFSIZE + KLOAD
    43                                  
    44                                  
    45                                  ; IBM PC/AT BIOS ----- 10/06/85 (postequ.inc)
    46                                  ;--------- CMOS TABLE LOCATION ADDRESS'S -------------------------------------
    47                                  CMOS_SECONDS	EQU	00H		; SECONDS (BCD)
    48                                  CMOS_SEC_ALARM	EQU	01H		; SECONDS ALARM (BCD)
    49                                  CMOS_MINUTES	EQU	02H		; MINUTES (BCD)
    50                                  CMOS_MIN_ALARM	EQU	03H		; MINUTES ALARM (BCD) 	
    51                                  CMOS_HOURS	EQU	04H		; HOURS (BCD
    52                                  CMOS_HR_ALARM	EQU	005H		; HOURS ALARM   (BCD)
    53                                  CMOS_DAY_WEEK	EQU	06H		; DAY OF THE WEEK  (BCD)
    54                                  CMOS_DAY_MONTH	EQU	07H		; DAY OF THE MONTH (BCD) 
    55                                  CMOS_MONTH	EQU	08H		; MONTH (BCD)
    56                                  CMOS_YEAR	EQU	09H		; YEAR (TWO DIGITS) (BCD)
    57                                  CMOS_CENTURY	EQU	32H		; DATE CENTURY BYTE (BCD)
    58                                  CMOS_REG_A	EQU	0AH		; STATUS REGISTER A
    59                                  CMOS_REG_B	EQU	00BH		; STATUS REGISTER B  ALARM
    60                                  CMOS_REG_C	EQU	00CH		; STATUS REGISTER C  FLAGS
    61                                  CMOS_REG_D	EQU	0DH		; STATUS REGISTER D  BATTERY
    62                                  CMOS_SHUT_DOWN	EQU	0FH		; SHUTDOWN STATUS COMMAND BYTE
    63                                  ;----------------------------------------
    64                                  ;	CMOS EQUATES FOR THIS SYSTEM	;
    65                                  ;-----------------------------------------------------------------------------
    66                                  CMOS_PORT	EQU	070H		; I/O ADDRESS OF CMOS ADDRESS PORT
    67                                  CMOS_DATA	EQU	071H		; I/O ADDRESS OF CMOS DATA PORT
    68                                  NMI		EQU	10000000B	; DISABLE NMI INTERRUPTS MASK -
    69                                  					; HIGH BIT OF CMOS LOCATION ADDRESS
    70                                  
    71                                  ; Memory Allocation Table Address
    72                                  ; 05/11/2014
    73                                  ; 31/10/2014
    74                                  MEM_ALLOC_TBL	equ	100000h		; Memory Allocation Table at the end of
    75                                  					; the 1st 1 MB memory space.
    76                                  					; (This address must be aligned
    77                                  					;  on 128 KB boundary, if it will be
    78                                  					;  changed later.)
    79                                  					; ((lower 17 bits of 32 bit M.A.T.
    80                                  					;   address must be ZERO)).
    81                                  					; ((((Reason: 32 bit allocation 
    82                                  					;     instructions, dword steps)))
    83                                  					; (((byte >> 12 --> page >> 5)))  
    84                                  ;04/11/2014	
    85                                  PDE_A_PRESENT	equ	1		; Present flag for PDE
    86                                  PDE_A_WRITE	equ 	2		; Writable (write permission) flag
    87                                  PDE_A_USER	equ	4		; User (non-system/kernel) page flag
    88                                  ;
    89                                  PTE_A_PRESENT	equ	1		; Present flag for PTE (bit 0)
    90                                  PTE_A_WRITE	equ 	2		; Writable (write permission) flag (bit 1)
    91                                  PTE_A_USER	equ	4		; User (non-system/kernel) page flag (bit 2)
    92                                  PTE_A_ACCESS    equ	32		; Accessed flag (bit 5) ; 09/03/2015
    93                                  
    94                                  ; 17/02/2015 (unix386.s)
    95                                  ; 10/12/2014 - 30/12/2014 (0B000h -> 9000h) (dsectrm2.s)
    96                                  DPT_SEGM equ 09000h  ; FDPT segment (EDD v1.1, EDD v3)
    97                                  ;
    98                                  HD0_DPT	 equ 0	    ; Disk parameter table address for hd0
    99                                  HD1_DPT	 equ 32	    ; Disk parameter table address for hd1
   100                                  HD2_DPT	 equ 64	    ; Disk parameter table address for hd2
   101                                  HD3_DPT	 equ 96	    ; Disk parameter table address for hd3
   102                                  
   103                                  ; 15/11/2020
   104                                  VBE3INFOSEG equ 97E0h ; 512 bytes before Video_Pg_Backup
   105                                  ; 29/11/2020
   106                                  VBE3INFOBLOCK equ 97E00h ; linear address (512 bytes)
   107                                  VBE3MODEINFOBLOCK equ 97C00h ; linear address (256 bytes)
   108                                  VBE3SAVERESTOREBLOCK equ 97600h ; linear address (2048 bytes)
   109                                  VBE3CRTCINFOBLOCK equ 97D00h ; linear address (64 bytes)
   110                                  VBE3BIOSDATABLOCK equ 97000h ; linear address (1536 bytes)
   111                                  VBE3STACKADDR equ 96000h ; linear address (1024 bytes)
   112                                  ; VBE3 32 bit Protected Mode Interface (16 bit) Selectors (in GDT)
   113                                  VBE3CS equ 30h ; _vbe3_CS:
   114                                  VBE3BDS equ 38h ; _vbe3_BDS:
   115                                  VBE3A000 equ 40h ; _A0000Sel:
   116                                  VBE3B000 equ 48h ; _B0000Sel:
   117                                  VBE3B800 equ 50h ; _B8000Sel:
   118                                  VBE3DS equ 58h ; _vbe3_DS:
   119                                  VBE3SS equ 60h ; _vbe3_SS:
   120                                  VBE3ES equ 68h ; _vbe3_ES:
   121                                  KCODE16 equ 70h ; _16bit_CS:
   122                                  ;
   123                                  
   124                                  ; FDPT (Phoenix, Enhanced Disk Drive Specification v1.1, v3.0)
   125                                  ;      (HDPT: Programmer's Guide to the AMIBIOS, 1993)
   126                                  ;
   127                                  FDPT_CYLS	equ 0 ; 1 word, number of cylinders
   128                                  FDPT_HDS	equ 2 ; 1 byte, number of heads
   129                                  FDPT_TT		equ 3 ; 1 byte, A0h = translated FDPT with logical values
   130                                  		      ; otherwise it is standard FDPT with physical values 	
   131                                  FDPT_PCMP	equ 5 ; 1 word, starting write precompensation cylinder
   132                                  		      ; (obsolete for IDE/ATA drives)
   133                                  FDPT_CB		equ 8 ; 1 byte, drive control byte
   134                                  			; Bits 7-6 : Enable or disable retries (00h = enable)
   135                                  			; Bit 5	: 1 = Defect map is located at last cyl. + 1
   136                                  			; Bit 4 : Reserved. Always 0
   137                                  			; Bit 3 : Set to 1 if more than 8 heads
   138                                  			; Bit 2-0 : Reserved. Alsways 0
   139                                  FDPT_LZ		equ 12 ; 1 word, landing zone (obsolete for IDE/ATA drives)
   140                                  FDPT_SPT	equ 14 ; 1 byte, sectors per track
   141                                  
   142                                  ; Floppy Drive Parameters Table (Programmer's Guide to the AMIBIOS, 1993)
   143                                  ; (11 bytes long) will be used by diskette handler/bios
   144                                  ; which is derived from IBM PC-AT BIOS (DISKETTE.ASM, 21/04/1986).
   145                                  
   146                                  ; 01/02/2016
   147                                  Logical_DOSDisks equ 90000h + 100h ; 26*256 = 6656 bytes
   148                                  Directory_Buffer equ 80000h ; max = 64K Bytes
   149                                  FAT_Buffer	 equ 91C00h ; 1536 bytes (3 sectors)
   150                                  ; 15/02/2016
   151                                  Cluster_Buffer	 equ 70000h ; max = 64K Bytes ; buffer for file read & write
   152                                  ; 11/04/2016
   153                                  Env_Page:	 equ 93000h ; 512 bytes (4096 bytes)
   154                                  Env_Page_Size	 equ 512    ; (4096 bytes)
   155                                  ; 30/07/2016
   156                                  Video_Pg_Backup	 equ 98000h ; Mode 3h, video page backup (32K, 8 pages)
   157                                  
   158                                  ; 29/11/2020
   159                                  ; Free/Reserved memory blocks (in 1st 1MB): 93200h to 96000h (available)
   160                                  
   161                                  
   162                                  [BITS 16]       ; We need 16-bit intructions for Real mode
   163                                  
   164                                  [ORG 0] 
   165                                  	; 12/11/2014
   166                                  	; Save boot drive number (that is default root drive)
   167 00000000 8816[AA64]              	mov	[boot_drv], dl ; physical drv number
   168                                  
   169                                  	; Determine installed memory
   170                                  	; 31/10/2014
   171                                  	;
   172 00000004 B801E8                  	mov	ax, 0E801h ; Get memory size 
   173 00000007 CD15                    	int	15h	   ; for large configurations
   174 00000009 7308                    	jnc	short chk_ms
   175 0000000B B488                    	mov	ah, 88h    ; Get extended memory size 
   176 0000000D CD15                    	int	15h
   177                                  	;	   
   178                                  	;mov	al, 17h	; Extended memory (1K blocks) low byte
   179                                  	;out	70h, al ; select CMOS register
   180                                  	;in	al, 71h ; read data (1 byte)
   181                                  	;mov	cl, al
   182                                  	;mov	al, 18h ; Extended memory (1K blocks) high byte
   183                                  	;out	70h, al ; select CMOS register
   184                                  	;in	al, 71h ; read data (1 byte)
   185                                  	;mov	ch, al
   186                                   	;      
   187 0000000F 89C1                    	mov	cx, ax
   188 00000011 31D2                    	xor	dx, dx
   189                                  chk_ms:
   190 00000013 890E[A664]              	mov	[mem_1m_1k], cx
   191 00000017 8916[A864]              	mov	[mem_16m_64k], dx
   192                                  	; 05/11/2014
   193                                  	;and	dx, dx
   194                                  	;jz	short L2
   195 0000001B 81F90004                        cmp     cx, 1024
   196                                  	;jnb	short L0
   197 0000001F 7351                    	jnb	short V0 ; 14/11/2020
   198                                  		 ; insufficient memory_error	
   199                                  		 ; Minimum 2 MB memory is needed... 
   200                                  	; 05/11/2014
   201                                  	; (real mode error printing)
   202 00000021 FB                      	sti
   203 00000022 BE[3600]                	mov	si, msg_out_of_memory
   204 00000025 BB0700                  	mov	bx, 7
   205 00000028 B40E                    	mov	ah, 0Eh	; write tty
   206                                  oom_1:
   207 0000002A AC                      	lodsb
   208 0000002B 08C0                    	or	al, al
   209 0000002D 7404                    	jz	short oom_2
   210 0000002F CD10                    	int	10h
   211 00000031 EBF7                    	jmp	short oom_1
   212                                  oom_2:
   213 00000033 F4                              hlt
   214 00000034 EBFD                    	jmp	short oom_2
   215                                  
   216                                  ; 20/02/2017
   217                                  ; 05/11/2014
   218                                  msg_out_of_memory:
   219 00000036 070D0A                  	db 	07h, 0Dh, 0Ah
   220 00000039 496E73756666696369-             db      'Insufficient memory !'
   220 00000042 656E74206D656D6F72-
   220 0000004B 792021             
   221 0000004E 0D0A                    	db	0Dh, 0Ah
   222                                  _int13h_48h_buffer: ; 07/07/2016
   223 00000050 284D696E696D756D20-     	db	'(Minimum 2MB memory is needed.)'
   223 00000059 324D42206D656D6F72-
   223 00000062 79206973206E656564-
   223 0000006B 65642E29           
   224 0000006F 0D0A00                   	db	0Dh, 0Ah, 0
   225                                  V0:
   226                                  	; 15/11/2020
   227                                  	; 14/11/2020 (TRDOS 386 v2.0.3)
   228                                  	; check VESA (VBE) VIDEO BIOS version
   229                                  
   230 00000072 B8034F                  	mov	ax, 4F03h  ; Return current VBE mode
   231 00000075 CD10                    	int	10h
   232 00000077 83F84F                  	cmp	ax, 004Fh  ; successful (vbe) function call
   233 0000007A 752B                    	jne	short L0   ; not a VESA VBE compatible bios	
   234                                  
   235                                  	;mov	ah, 3
   236                                  	;;jmp	short v1	
   237                                  	
   238                                  	; 15/11/2020
   239 0000007C BBE097                  	mov	bx, VBE3INFOSEG  ; 97E0h for current version 
   240 0000007F 8EC3                    	mov	es, bx
   241 00000081 31FF                    	xor	di, di
   242 00000083 2666C70556424532        	mov	dword [es:di], 'VBE2' ; request VESA VBE3 info
   243                                  		; es:di = buffer address (512 bytes)
   244                                  	;mov	ax, 4F00h ; Return VBE controller information
   245 0000008B 86C4                    	xchg	al, ah
   246 0000008D CD10                    	int	10h
   247                                  	
   248                                  	; dx = cs
   249                                  	; es = VBE3INFOSEG (97E0h)
   250                                  	; di = 0
   251                                  	; ss = (endofkernelfile/16)+16
   252                                  	; sp = 0FFFEh
   253                                  
   254 0000008F 83F84F                  	cmp	ax, 004Fh
   255 00000092 7511                    	jne	short V1 ; old vga bios (not VESA compatible)
   256                                  
   257                                  	; 15/11/2020
   258 00000094 2666813D56455341        	cmp	dword [es:di], 'VESA'
   259 0000009C 7507                    	jne	short V1
   260                                  	
   261                                  	;mov	ax, [es:di+4]
   262                                  	;	; ax = vbe version in BCD format (0200h or 0300h)
   263                                  	;mov	[vbe3], ah ; version number (major) 	
   264                                  
   265                                  	; 15/11/2020
   266 0000009E 268A4505                	mov	al, [es:di+5]
   267                                  		; al = high byte of VBE version number (02h or 03h)
   268                                  
   269 000000A2 A2[CB08]                	mov	[vbe3], al ; version number (major) 	
   270                                  			   ; 02h or 03h is expected
   271                                  V1:
   272 000000A5 1E                      	push	ds
   273 000000A6 07                      	pop	es ; restore extra data segment		
   274                                  L0:
   275                                  
   276                                  %include 'diskinit.s' ; 07/03/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.2 - diskinit.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 29/08/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.14 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; diskinit.inc (10/07/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - DISKINIT.INC
    20                              <1> ; Last Modification: 10/07/2015
    21                              <1> 
    22                              <1> ; DISK I/O SYSTEM INITIALIZATION - Erdogan Tan (Retro UNIX 386 v1 project)
    23                              <1> 
    24                              <1> ; ///////// DISK I/O SYSTEM STRUCTURE INITIALIZATION ///////////////
    25                              <1> 
    26                              <1> 	; 29/08/2020
    27                              <1> 	; 17/07/2020
    28                              <1> 	; 14/07/2020 (TRDOS 386 v2.0.2)
    29                              <1> 	; 10/12/2014 - 02/02/2015 - dsectrm2.s
    30                              <1> ;L0:
    31                              <1> 	; 12/11/2014 (Retro UNIX 386 v1 - beginning)
    32                              <1> 	; Detecting disk drives... (by help of ROM-BIOS)
    33 000000A7 BA7F00              <1> 	mov	dx, 7Fh
    34                              <1> L1:	
    35 000000AA FEC2                <1> 	inc	dl
    36 000000AC B441                <1> 	mov	ah, 41h ; Check extensions present
    37                              <1> 			; Phoenix EDD v1.1 - EDD v3
    38 000000AE BBAA55              <1> 	mov	bx, 55AAh
    39 000000B1 CD13                <1> 	int 	13h
    40 000000B3 721A                <1> 	jc	short L2
    41                              <1> 
    42 000000B5 81FB55AA            <1> 	cmp	bx, 0AA55h
    43 000000B9 7514                <1> 	jne	short L2
    44 000000BB FE06[AD64]          <1> 	inc	byte [hdc]	; count of hard disks (EDD present)
    45 000000BF 8816[AC64]          <1>         mov     [last_drv], dl  ; last hard disk number
    46 000000C3 BB[3064]            <1> 	mov	bx, hd0_type - 80h
    47 000000C6 01D3                <1> 	add	bx, dx	 
    48 000000C8 880F                <1> 	mov	[bx], cl ; Interface support bit map in CX
    49                              <1> 			 ; Bit 0 - 1, Fixed disk access subset ready
    50                              <1> 			 ; Bit 1 - 1, Drv locking and ejecting ready
    51                              <1> 			 ; Bit 2 - 1, Enhanced Disk Drive Support
    52                              <1>                          ;            (EDD) ready (DPTE ready)
    53                              <1> 			 ; Bit 3 - 1, 64bit extensions are present
    54                              <1>                          ;            (EDD-3)
    55                              <1> 			 ; Bit 4 to 15 - 0, Reserved
    56 000000CA 80FA83              <1> 	cmp	dl, 83h	 ; drive number < 83h
    57 000000CD 72DB                <1> 	jb	short L1
    58                              <1> L2:
    59                              <1> 	; 23/11/2014
    60                              <1> 	; 19/11/2014
    61 000000CF 30D2                <1> 	xor	dl, dl  ; 0
    62                              <1> 	; 04/02/2016 (esi -> si)
    63 000000D1 BE[AE64]            <1> 	mov	si, fd0_type
    64                              <1> L3:
    65                              <1> 	; 14/01/2015
    66 000000D4 8816[AB64]          <1> 	mov	[drv], dl
    67                              <1> 	;
    68 000000D8 B408                <1> 	mov 	ah, 08h ; Return drive parameters
    69 000000DA CD13                <1> 	int	13h	
    70 000000DC 7210                <1> 	jc	short L4
    71                              <1> 		; BL = drive type (for floppy drives)
    72                              <1> 		; DL = number of floppy drives
    73                              <1> 		;		
    74                              <1> 		; ES:DI = Address of DPT from BIOS
    75                              <1> 		;
    76 000000DE 881C                <1> 	mov	[si], bl ;  Drive type
    77                              <1> 			; 4 = 1.44 MB, 80 track, 3 1/2"
    78                              <1> 	; 14/01/2015
    79 000000E0 E8DE01              <1> 	call	set_disk_parms
    80                              <1> 	; 10/12/2014
    81 000000E3 81FE[AE64]          <1> 	cmp	si, fd0_type
    82 000000E7 7705                <1> 	ja	short L4
    83 000000E9 46                  <1> 	inc	si ; fd1_type
    84 000000EA B201                <1> 	mov	dl, 1
    85 000000EC EBE6                <1> 	jmp	short L3
    86                              <1> L4:
    87 000000EE B27F                <1> 	mov	dl, 7Fh
    88                              <1> 	; 24/12/2014
    89 000000F0 803E[AD64]00        <1> 	cmp	byte [hdc], 0 ; EDD present or not ?	
    90 000000F5 0F878700            <1>         ja      L10       ; yes, all fixed disk operations
    91                              <1> 			  ; will be performed according to
    92                              <1> 			  ; present EDD specification
    93                              <1> 
    94                              <1> 	; 17/07/2020
    95                              <1> 	; Note: Virtual CPU will not come here while 
    96                              <1> 	; running in QEMU, Bochs, VirtualBox emulators !!!
    97                              <1> 	
    98                              <1> 	; 17/07/2020
    99                              <1> 	; Older BIOS (INT 13h, AH = 48h is not available)
   100                              <1> L6:
   101 000000F9 FEC2                <1> 	inc 	dl
   102 000000FB 8816[AB64]          <1>         mov     [drv], dl
   103 000000FF 8816[AC64]          <1>         mov     [last_drv], dl ; 14/01/2015
   104 00000103 B408                <1> 	mov 	ah, 08h ; Return drive parameters
   105 00000105 CD13                <1> 	int	13h	; (conventional function)
   106 00000107 0F82A801            <1>         jc      L13	; fixed disk drive not ready
   107 0000010B 8816[AD64]          <1>         mov     [hdc], dl ; number of drives
   108                              <1> 	;; 14/01/2013
   109                              <1> 	;;push	cx
   110 0000010F E8AF01              <1> 	call	set_disk_parms
   111                              <1> 	;;pop	cx
   112                              <1> 	;
   113                              <1> 	;;and	cl, 3Fh	 ; sectors per track (bits 0-6)
   114 00000112 8A16[AB64]          <1>         mov     dl, [drv]
   115 00000116 BB0401              <1> 	mov	bx, 65*4 ; hd0 parameters table (INT 41h)	
   116 00000119 80FA80              <1> 	cmp	dl, 80h
   117 0000011C 7603                <1> 	jna	short L7
   118 0000011E 83C314              <1> 	add	bx, 5*4	 ; hd1 parameters table (INT 46h)
   119                              <1> L7:	
   120 00000121 31C0                <1> 	xor	ax, ax
   121 00000123 8ED8                <1> 	mov	ds, ax
   122 00000125 8B37                <1>         mov     si, [bx]
   123 00000127 8B4702              <1>         mov     ax, [bx+2] 
   124 0000012A 8ED8                <1> 	mov	ds, ax
   125 0000012C 3A4C0E              <1>         cmp     cl, [si+FDPT_SPT] ; sectors per track 
   126 0000012F 0F857C01            <1>         jne     L12 ; invalid FDPT
   127 00000133 BF0000              <1> 	mov	di, HD0_DPT
   128 00000136 80FA80              <1> 	cmp	dl, 80h
   129 00000139 7603                <1> 	jna	short L8
   130 0000013B BF2000              <1> 	mov	di, HD1_DPT 
   131                              <1> L8:
   132                              <1> 	; 30/12/2014
   133 0000013E B80090              <1> 	mov	ax, DPT_SEGM
   134 00000141 8EC0                <1> 	mov	es, ax
   135                              <1> 	; 24/12/2014
   136 00000143 B90800              <1> 	mov	cx, 8
   137 00000146 F3A5                <1> 	rep	movsw  ; copy 16 bytes to the kernel's DPT location
   138 00000148 8CC8                <1> 	mov	ax, cs
   139 0000014A 8ED8                <1> 	mov	ds, ax
   140                              <1> 
   141                              <1> 	; 02/02/2015
   142                              <1> 	;mov	cl, [drv]
   143                              <1> 	;mov	bl, cl
   144                              <1> 	;mov	ax, 1F0h
   145                              <1> 	;and	bl, 1
   146                              <1> 	;jz	short L9
   147                              <1> 	;shl	bl, 4
   148                              <1> 	;sub	ax, 1F0h-170h
   149                              <1> 
   150                              <1> 	; 17/07/2020 
   151                              <1> 	; (Only 1F0h port address must be valid for old ROM BIOSes)
   152 0000014C B8F001              <1> 	mov	ax, 1F0h
   153 0000014F B3A0                <1> 	mov	bl, 0A0h
   154 00000151 80FA80              <1> 	cmp	dl, 80h
   155 00000154 7603                <1> 	jna	short L9
   156                              <1> 	; dl = 81h
   157 00000156 80C310              <1> 	add	bl, 10h  ; slave disk
   158                              <1> 	;sub	ax, 1F0h-170h
   159                              <1> L9:
   160 00000159 AB                  <1> 	stosw	; I/O PORT Base Address (1F0h, 170h)
   161 0000015A 050602              <1> 	add	ax, 206h
   162 0000015D AB                  <1> 	stosw	; CONTROL PORT Address (3F6h, 376h)	
   163 0000015E 88D8                <1> 	mov	al, bl  ; bit 4, master/slave disk bit
   164                              <1> 	;add	al, 0A0h ; 17/07/2020
   165 00000160 AA                  <1> 	stosb	; Device/Head Register upper nibble
   166                              <1> 	;
   167 00000161 FE06[AB64]          <1> 	inc	byte [drv]
   168 00000165 BB[3064]            <1> 	mov	bx, hd0_type - 80h
   169 00000168 01CB                <1> 	add	bx, cx
   170 0000016A 800F80              <1>         or      byte [bx], 80h  ; present sign (when lower nibble is 0)
   171 0000016D A0[AD64]            <1> 	mov	al, [hdc]
   172 00000170 FEC8                <1> 	dec	al
   173 00000172 0F843D01            <1>         jz      L13
   174 00000176 80FA80              <1> 	cmp	dl, 80h
   175 00000179 0F867CFF            <1>         jna	L6 ; Max. 2 hard disks  ; 17/07/2020 
   176 0000017D E93301              <1>         jmp     L13
   177                              <1> L10:
   178 00000180 FEC2                <1> 	inc 	dl
   179                              <1> 	; 25/12/2014
   180 00000182 8816[AB64]          <1> 	mov	[drv], dl
   181 00000186 B408                <1> 	mov 	ah, 08h ; Return drive parameters
   182 00000188 CD13                <1> 	int	13h	; (conventional function)
   183 0000018A 0F822501            <1>         jc      L13
   184                              <1> 	; 14/01/2015
   185 0000018E 8A16[AB64]          <1> 	mov	dl, [drv]
   186 00000192 52                  <1> 	push	dx
   187 00000193 51                  <1> 	push	cx
   188 00000194 E82A01              <1> 	call	set_disk_parms
   189 00000197 59                  <1> 	pop	cx
   190 00000198 5A                  <1> 	pop	dx
   191                              <1> 	; 06/07/2016 (BugFix for >64K kernel files)
   192                              <1> 	; 04/02/2016 (esi -> si)
   193                              <1> 	;mov	si, _end ; 30 byte temporary buffer address 	
   194                              <1> 	;		 ; at the '_end' of kernel.
   195                              <1> 	;mov	word [si], 30
   196                              <1> 	; 06/07/2016
   197 00000199 BE[5000]            <1> 	mov	si, _int13h_48h_buffer
   198                              <1> 	; 09/07/2016
   199 0000019C B81E00              <1> 	mov	ax, 001Eh
   200 0000019F 8824                <1> 	mov	[si], ah ; 0
   201 000001A1 46                  <1> 	inc	si
   202 000001A2 8904                <1> 	mov	word [si], ax
   203                              <1>  	; word [si] = 30
   204                              <1> 	;
   205 000001A4 B448                <1> 	mov	ah, 48h	 ; Get drive parameters (EDD function)
   206 000001A6 CD13                <1> 	int	13h
   207 000001A8 0F820701            <1>         jc      L13
   208                              <1> 
   209                              <1> 	; 29/08/2020
   210                              <1> 	; 04/02/2016 (ebx -> bx)
   211                              <1> 	; 14/01/2015
   212 000001AC 28FF                <1> 	sub	bh, bh
   213 000001AE 88D3                <1> 	mov	bl, dl
   214                              <1> 	;sub	bl, 80h
   215                              <1> 	; 29/08/2020
   216 000001B0 81C3[3064]          <1> 	add	bx, (hd0_type - 80h)
   217                              <1> 	;mov 	al, [bx]
   218 000001B4 8A07                <1> 	mov	al, [bx]
   219 000001B6 0C80                <1> 	or	al, 80h
   220 000001B8 8807                <1> 	mov 	[bx], al	
   221 000001BA 81EB[AE64]          <1> 	sub	bx, hd0_type - 2 ; 15/01/2015
   222                              <1> 	;add	bx, drv.status
   223                              <1> 	;mov	[bx], al
   224                              <1> 	; 29/08/2020
   225 000001BE 8887[FA64]          <1> 	mov	[bx+drv.status], al
   226                              <1> 	; 04/02/2016 (eax -> ax)
   227                              <1> 	;mov	ax, [si+16]
   228                              <1> 	; 14/07/2020
   229                              <1> 	;mov	di, [si+18] 
   230                              <1> 	;;test	ax, [si+18]
   231                              <1> 	;test	ax, di ; 14/07/2020
   232                              <1> 	;jz	short L10_A0h ; (!) ; 17/07/2020
   233                              <1> 			; 'CHS only' disks on EDD system 
   234                              <1> 			;  are reported with ZERO disk size
   235                              <1> 			; (if so, we must not overwrite
   236                              <1> 			; calculated disk size in 'set_disk_parms')
   237                              <1> 	; 29/08/2020
   238 000001C2 8B4410              <1> 	mov	ax, [si+16]
   239 000001C5 8B7C12              <1> 	mov	di, [si+18]
   240 000001C8 09C0                <1> 	or	ax, ax
   241 000001CA 7504                <1> 	jnz	short L10_LBA
   242 000001CC 09FF                <1> 	or	di, di
   243 000001CE 740B                <1> 	jz	short L10_A0h
   244                              <1> L10_LBA:
   245                              <1> 	;sub	bx, drv.status
   246 000001D0 C1E302              <1> 	shl	bx, 2
   247                              <1> 	;add	bx, drv.size ; disk size (in sectors)
   248                              <1> 	;mov	[bx], ax
   249                              <1> 	; 29/08/2020
   250 000001D3 8987[DE64]          <1> 	mov	[bx+drv.size], ax
   251                              <1> 	;mov	ax, [si+18]
   252                              <1> 	;;mov	[bx], ax
   253                              <1> 	;mov	[bx+2], ax ; BugFix ; 15/07/2020
   254                              <1> 	; 14/07/2020
   255                              <1> 	;mov	[bx+2], di ; 15/07/2020
   256                              <1> 	; 29/08/2020
   257 000001D7 89BF[E064]          <1> 	mov	[bx+drv.size+2], di
   258                              <1> L10_A0h: 
   259                              <1> 	; 17/07/2020
   260                              <1> 	; Note: Virtual CPU will jump here from above (!) test
   261                              <1> 	;	while running in QEMU
   262                              <1> 
   263                              <1> 	; Jump here to fix a ZERO (LBA) disk size problem 
   264                              <1> 	; for CHS disks (28/02/2015)
   265                              <1> 	
   266                              <1> 	; 30/12/2014
   267 000001DB BF0000              <1> 	mov	di, HD0_DPT
   268 000001DE 88D0                <1> 	mov	al, dl
   269 000001E0 83E003              <1> 	and 	ax, 3
   270 000001E3 C0E005              <1> 	shl	al, 5 ; * 32
   271 000001E6 01C7                <1> 	add 	di, ax
   272 000001E8 B80090              <1> 	mov	ax, DPT_SEGM
   273 000001EB 8EC0                <1> 	mov	es, ax
   274                              <1> 	;
   275 000001ED 88E8                <1> 	mov	al, ch	; max. cylinder number (bits 0-7)
   276 000001EF 88CC                <1> 	mov	ah, cl	
   277 000001F1 C0EC06              <1> 	shr	ah, 6	; max. cylinder number (bits 8-9)
   278 000001F4 40                  <1>  	inc	ax	; logical cylinders (limit 1024)
   279 000001F5 AB                  <1> 	stosw		
   280 000001F6 88F0                <1> 	mov	al, dh	; max. head number
   281                              <1> 	;
   282 000001F8 30F6                <1> 	xor	dh, dh  ; 29/08/2020 (dh = 0 is needed here)
   283                              <1> 	;
   284 000001FA FEC0                <1> 	inc	al
   285 000001FC AA                  <1> 	stosb		; logical heads (limits 256)
   286 000001FD B0A0                <1> 	mov	al, 0A0h ; Indicates translated table
   287 000001FF AA                  <1> 	stosb
   288 00000200 8A440C              <1> 	mov	al, [si+12]
   289 00000203 AA                  <1> 	stosb		 ; physical sectors per track
   290 00000204 31C0                <1>  	xor	ax, ax
   291                              <1> 	;dec	ax	 ; 02/01/2015 
   292 00000206 AB                  <1> 	stosw		 ; precompensation (obsolete)
   293                              <1> 	;xor	al, al	 ; 02/01/2015	
   294 00000207 AA                  <1> 	stosb		 ; reserved
   295 00000208 B008                <1> 	mov	al, 8	 ; drive control byte
   296                              <1> 		         ; (do not disable retries, 
   297                              <1> 			 ; more than 8 heads)
   298 0000020A AA                  <1> 	stosb
   299 0000020B 8B4404              <1> 	mov	ax, [si+4]
   300 0000020E AB                  <1> 	stosw		 ; physical number of cylinders	
   301                              <1> 	;push	ax	 ; 02/01/2015
   302 0000020F 8A4408              <1> 	mov	al, [si+8]
   303 00000212 AA                  <1> 	stosb		 ; physical num. of heads (limit 16)
   304 00000213 29C0                <1> 	sub 	ax, ax
   305                              <1> 	;pop	ax	 ; 02/01/2015	
   306 00000215 AB                  <1> 	stosw		 ; landing zone (obsolete)
   307 00000216 88C8                <1> 	mov	al, cl	 ; logical sectors per track (limit 63)
   308 00000218 243F                <1> 	and 	al, 3Fh	
   309 0000021A AA                  <1> 	stosb
   310                              <1> 	;sub	al, al	 ; checksum
   311                              <1> 	;stosb
   312                              <1> 	;
   313 0000021B 83C61A              <1> 	add	si, 26   ; (BIOS) DPTE address pointer
   314 0000021E AD                  <1> 	lodsw
   315 0000021F 50                  <1> 	push	ax ; *	 ; (BIOS) DPTE offset
   316 00000220 AD                  <1> 	lodsw
   317 00000221 50                  <1> 	push	ax ; **	 ; (BIOS) DPTE segment
   318                              <1> 	;
   319                              <1> 	; checksum calculation
   320 00000222 89FE                <1> 	mov	si, di
   321 00000224 06                  <1> 	push	es
   322 00000225 1F                  <1> 	pop	ds
   323                              <1> 	;mov	cx, 16
   324 00000226 B90F00              <1> 	mov 	cx, 15
   325 00000229 29CE                <1> 	sub	si, cx
   326 0000022B 30E4                <1> 	xor	ah, ah
   327                              <1> 	;del	cl
   328                              <1> L11:		
   329 0000022D AC                  <1> 	lodsb
   330 0000022E 00C4                <1> 	add	ah, al
   331 00000230 E2FB                <1> 	loop	L11
   332                              <1> 	;
   333 00000232 88E0                <1> 	mov	al, ah
   334 00000234 F6D8                <1> 	neg	al	; -x+x = 0
   335 00000236 AA                  <1> 	stosb		; put checksum in byte 15 of the tbl
   336                              <1> 	;
   337 00000237 1F                  <1> 	pop	ds ; **	; (BIOS) DPTE segment
   338 00000238 5E                  <1> 	pop	si ; *	; (BIOS) DPTE offset	
   339                              <1> 	;
   340                              <1> 	; 14/07/2020
   341                              <1> 	; 0FFFFh:0FFFFh = invalid DPTE address
   342 00000239 8B0C                <1> 	mov	cx, [si]
   343 0000023B 8B4402              <1> 	mov	ax, [si+2]
   344 0000023E 21C1                <1> 	and	cx, ax
   345 00000240 41                  <1> 	inc	cx 
   346 00000241 7404                <1> 	jz	short L11c ; 0FFFFh:0FFFFh
   347 00000243 0B04                <1> 	or	ax, [si]
   348 00000245 752A                <1> 	jnz	short L11e ; <> 0
   349                              <1> L11c:
   350                              <1> 	; 17/07/2020
   351                              <1> 	; TRDOS 386 v2 DRVINIT assumptions:
   352                              <1> 	; (also by regarding QEMU, Bochs and VirtualBox settings)
   353                              <1> 	;	Hard disk 0 port address: 1F0h
   354                              <1> 	;	Hard disk 1 port address: 1F0h
   355                              <1> 	;	Hard disk 2 port address: 170h
   356                              <1> 	;	Hard disk 3 port address: 170h
   357                              <1> 
   358                              <1> 	; in QEMU, hda=hd0 (1F0h) and hdb=hd1 (1F0h) -IRQ14-
   359                              <1> 	;      and hdc=hd2 (170h) and hdd=hd3 (170h) -IRQ15-
   360                              <1> 
   361 00000247 B8F001              <1> 	mov	ax, 1F0h
   362                              <1> 
   363                              <1> 	; 15/07/2020
   364                              <1> 	; 14/07/2020
   365                              <1> 	; Invalid DPTE address...
   366                              <1> 	; Default DPTE parms must be set for DISK_IO_CONT
   367                              <1> 	; (diskio.s)
   368                              <1> 	; 17/07/2020
   369                              <1> 
   370                              <1> 	;mov	bl, dl
   371                              <1> 	;and	bl, 1
   372                              <1> 	;jz	short L11d
   373                              <1> 
   374 0000024A B3A0                <1> 	mov	bl, 0A0h
   375                              <1> 
   376 0000024C F6C201              <1> 	test	dl, 1
   377 0000024F 7403                <1> 	jz	short L11g  ; Master (as default, for 80h & 82h))
   378                              <1> 	;shl	bl, 4 ; bl = 16 (bit 4 = 1 -> slave)
   379 00000251 80C310              <1> 	add	bl, 10h  ; Slave (as default, for 81h & 83h)
   380                              <1> L11g:
   381                              <1> 	; 17/07/2020
   382 00000254 80FA82              <1> 	cmp	dl, 82h	; Hard disk 3 or 4 ?
   383 00000257 7203                <1> 	jb	short L11d ; Primary ATA channel (hd0, hd1)
   384                              <1> 			   ; (port address = 1F0h)
   385                              <1> 	
   386                              <1> 	; Secondary ATA channel (hd2, hd3)
   387                              <1> 	; (port address = 170h)
   388                              <1> 
   389 00000259 2D8000              <1> 	sub	ax, 1F0h-170h
   390                              <1> L11d:
   391                              <1> 	; 14/07/2020
   392 0000025C AB                  <1> 	stosw	; I/O PORT Base Address (1F0h, 170h)
   393 0000025D 050602              <1> 	add	ax, 206h
   394 00000260 AB                  <1> 	stosw	; CONTROL PORT Address (3F6h, 376h)	
   395 00000261 88D8                <1> 	mov	al, bl  ; Master/Slave bit (0 = Master)
   396                              <1> 	; 17/07/2020
   397                              <1> 	;or	al, 0A0h ; CHS (LBA enable bit = 0)
   398                              <1> 			 ; (Bits 5&7, reserved bits  =  1)
   399 00000263 30E4                <1> 	xor	ah, ah
   400                              <1> 	;stosb	; Device/Head Register upper nibble
   401 00000265 AB                  <1> 	stosw
   402 00000266 30C0                <1> 	xor	al, al
   403 00000268 B90500              <1> 	mov	cx, 5
   404 0000026B F3AB                <1> 	rep	stosw ; clear remain part of the (fake) DPTE
   405 0000026D 0E                  <1> 	push	cs
   406 0000026E 1F                  <1> 	pop	ds
   407 0000026F EB2E                <1> 	jmp	short L11f
   408                              <1> L11e:
   409                              <1> 	; 23/02/2015
   410 00000271 57                  <1> 	push	di
   411                              <1> 	; ES:DI points to DPTE (FDPTE) location
   412                              <1> 	;;mov	cx, 8
   413                              <1> 	;mov	cl, 8
   414 00000272 B90800              <1> 	mov	cx, 8 ; 14/07/2020
   415 00000275 F3A5                <1> 	rep	movsw	
   416                              <1> 	;
   417                              <1> 	; 23/02/2015
   418                              <1> 	; (P)ATA drive and LBA validation
   419                              <1> 	; (invalidating SATA drives and setting
   420                              <1> 	; CHS type I/O for old type fixed disks)
   421 00000277 5B                  <1> 	pop	bx
   422 00000278 8CC8                <1> 	mov	ax, cs
   423 0000027A 8ED8                <1> 	mov	ds, ax
   424 0000027C 268B07              <1> 	mov	ax, [es:bx]
   425 0000027F 3DF001              <1> 	cmp	ax, 1F0h
   426 00000282 7413                <1> 	je	short L11a
   427 00000284 3D7001              <1> 	cmp	ax, 170h
   428 00000287 740E                <1> 	je	short L11a
   429                              <1> 	; invalidation 
   430                              <1> 	; (because base port address is not 1F0h or 170h)
   431                              <1> 	;xor	bh, bh
   432                              <1> 	;mov	bl, dl
   433                              <1> 	; 29/08/2020
   434                              <1> 	;xor	dh, dh ; 0
   435 00000289 89D3                <1> 	mov	bx, dx
   436                              <1> 	;sub	bl, 80h
   437                              <1> 	;mov	byte [bx+hd0_type], 0 ; not a valid disk drive !		
   438                              <1>         ;or	byte [bx+drv.status+2], 0F0h ; (failure sign)
   439                              <1> 	; 29/08/2020
   440 0000028B C687[3064]00        <1> 	mov	byte [bx+hd0_type-80h], 0
   441 00000290 808F[7C64]F0        <1> 	or	byte [bx+drv.status-7Eh], 0F0h
   442 00000295 EB0F                <1> 	jmp	short L11b
   443                              <1> L11a:	
   444                              <1> 	; LBA validation
   445 00000297 268A4704            <1> 	mov	al, [es:bx+4] ; Head register upper nibble
   446 0000029B A840                <1> 	test	al, 40h ; LBA bit (bit 6)
   447 0000029D 7507                <1> 	jnz	short L11b ; LBA type I/O is OK! (E0h or F0h)
   448                              <1> L11f:
   449                              <1> 	; force CHS type I/O for this drive (A0h or B0h)
   450                              <1> 	;sub	bh, bh
   451                              <1> 	;mov	bl, dl
   452                              <1> 	; 29/08/2020
   453                              <1> 	;xor	dh, dh ; 0
   454 0000029F 89D3                <1> 	mov	bx, dx
   455                              <1> 	;sub	bl, 80h ; 26/02/2015
   456                              <1>         ;and	byte [bx+drv.status+2], 0FEh ; clear bit 0
   457                              <1> 				; bit 0 = LBA ready bit
   458                              <1> 	; 29/08/2020
   459 000002A1 80A7[7C64]FE        <1> 	and	byte [bx+drv.status-7Eh], 0FEh
   460                              <1> 	; 'diskio' procedure will check this bit !
   461                              <1> L11b:
   462 000002A6 3A16[AC64]          <1> 	cmp	dl, [last_drv] ; 25/12/2014
   463 000002AA 7307                <1>         jnb     short L13
   464 000002AC E9D1FE              <1>         jmp     L10
   465                              <1> 
   466                              <1> L12:
   467                              <1> 	; Restore data registers
   468 000002AF 8CC8                <1> 	mov	ax, cs
   469 000002B1 8ED8                <1> 	mov	ds, ax	
   470                              <1> L13:
   471                              <1> 	; 13/12/2014
   472 000002B3 0E                  <1> 	push	cs
   473 000002B4 07                  <1> 	pop	es
   474                              <1> L14:
   475                              <1> 	; clear keyboard buffer
   476 000002B5 B411                <1> 	mov 	ah, 11h
   477 000002B7 CD16                <1> 	int 	16h
   478 000002B9 744D                <1> 	jz 	short L16 ; no keys in keyboard buffer
   479 000002BB B010                <1> 	mov	al, 10h
   480 000002BD CD16                <1> 	int 	16h
   481 000002BF EBF4                <1> 	jmp 	short L14
   482                              <1> 
   483                              <1> set_disk_parms:
   484                              <1> 	; 29/08/2020
   485                              <1> 	; 04/02/2016 (ebx -> bx)
   486                              <1> 	; 10/07/2015
   487                              <1> 	; 14/01/2015
   488                              <1> 	;push	bx
   489 000002C1 28FF                <1> 	sub	bh, bh
   490 000002C3 8A1E[AB64]          <1> 	mov	bl, [drv]
   491 000002C7 80FB80              <1> 	cmp	bl, 80h
   492 000002CA 7203                <1> 	jb	short sdp0
   493 000002CC 80EB7E              <1> 	sub	bl, 7Eh
   494                              <1> sdp0:	
   495                              <1> 	;add	bx, drv.status
   496                              <1>   	;mov	byte [bx], 80h ; 'Present' flag
   497                              <1> 	; 29/08/2020
   498 000002CF C687[FA64]80        <1> 	mov	byte [bx+drv.status], 80h
   499                              <1> 	;
   500 000002D4 88E8                <1> 	mov	al, ch ; last cylinder (bits 0-7)
   501 000002D6 88CC                <1> 	mov	ah, cl ; 
   502 000002D8 C0EC06              <1> 	shr	ah, 6  ; last cylinder (bits 8-9)
   503                              <1> 	;sub	bx, drv.status
   504 000002DB D0E3                <1> 	shl	bl, 1
   505                              <1> 	;add	bx, drv.cylinders
   506 000002DD 40                  <1> 	inc	ax  ; convert max. cyl number to cyl count		
   507                              <1> 	;mov	[bx], ax
   508                              <1> 	; 29/08/2020
   509 000002DE 8987[B464]          <1> 	mov	[bx+drv.cylinders], ax
   510 000002E2 50                  <1> 	push	ax ; ** cylinders
   511                              <1> 	;sub	bx, drv.cylinders
   512                              <1> 	;add	bx, drv.heads
   513 000002E3 30E4                <1> 	xor	ah, ah
   514 000002E5 88F0                <1> 	mov	al, dh ; heads
   515 000002E7 40                  <1> 	inc	ax
   516                              <1> 	;mov	[bx], ax
   517                              <1> 	; 29/08/2020
   518 000002E8 8987[C264]          <1>         mov	[bx+drv.heads], ax
   519                              <1> 	;sub     bx, drv.heads
   520                              <1>         ;add     bx, drv.spt
   521 000002EC 30ED                <1> 	xor	ch, ch
   522 000002EE 80E13F              <1> 	and	cl, 3Fh	; sectors (bits 0-6)
   523                              <1> 	;mov	[bx], cx
   524                              <1>         ; 29/08/2020
   525 000002F1 898F[D064]          <1> 	mov	[bx+drv.spt], cx
   526                              <1> 	;sub	bx, drv.spt
   527 000002F5 D1E3                <1> 	shl	bx, 1
   528                              <1> 	;add	bx, drv.size ; disk size (in sectors)
   529                              <1> 	; LBA size = cylinders * heads * secpertrack
   530 000002F7 F7E1                <1> 	mul	cx 
   531 000002F9 89C2                <1> 	mov	dx, ax	; heads*spt					
   532 000002FB 58                  <1> 	pop	ax ; ** cylinders
   533 000002FC 48                  <1> 	dec	ax ; 1 cylinder reserved (!?)
   534 000002FD F7E2                <1> 	mul	dx ; cylinders * (heads*spt)		
   535                              <1> 	;mov	[bx], ax
   536                              <1> 	;mov	[bx+2], dx
   537                              <1> 	; 29/08/2020
   538 000002FF 8987[DE64]          <1> 	mov	[bx+drv.size], ax
   539 00000303 8997[E064]          <1> 	mov	[bx+drv.size+2], dx
   540                              <1> 	;
   541                              <1> 	;pop	bx
   542 00000307 C3                  <1> 	retn
   543                              <1> 
   544                              <1> L16:	; 28/05/2016
   277                                  
   278                                  	; 10/11/2014
   279 00000308 FA                           	cli	; Disable interrupts (clear interrupt flag)
   280                                  		; Reset Interrupt MASK Registers (Master&Slave)
   281                                  	;mov	al, 0FFh	; mask off all interrupts
   282                                  	;out	21h, al		; on master PIC (8259)
   283                                  	;jmp 	$+2  ; (delay)
   284                                  	;out	0A1h, al	; on slave PIC (8259)
   285                                  	;
   286                                  	; Disable NMI 
   287 00000309 B080                    	mov   	al, 80h 
   288 0000030B E670                    	out   	70h, al		; set bit 7 to 1 for disabling NMI
   289                                  	;23/02/2015
   290                                  	;nop			;
   291                                  	;in	al, 71h		; read in 71h just after writing out to 70h
   292                                  				; for preventing unknown state (!?)
   293                                  	;
   294                                   	; 20/08/2014
   295                                  	; Moving the kernel 64 KB back (to physical address 0)
   296                                  	; DS = CS = 1000h
   297                                  	; 05/11/2014
   298 0000030D 31C0                    	xor	ax, ax
   299 0000030F 8EC0                    	mov	es, ax ; ES = 0
   300                                  	;
   301                                  	; 04/07/2016 -  TRDOS 386 (64K - 128K kernel)
   302 00000311 31F6                          	xor	si, si
   303 00000313 31FF                    	xor	di, di
   304 00000315 B90040                  	mov	cx, 16384
   305 00000318 F366A5                  	rep	movsd
   306                                  	;
   307 0000031B 06                      	push	es ; 0
   308 0000031C 68[2003]                	push	L17
   309 0000031F CB                      	retf
   310                                  L17:
   311 00000320 B90010                  	mov	cx, 1000h
   312 00000323 8EC1                    	mov	es, cx  ; 1000h 
   313 00000325 01C9                    	add	cx, cx
   314 00000327 8ED9                    	mov	ds, cx  ; 2000h
   315 00000329 29F6                    	sub	si, si
   316 0000032B 29FF                    	sub	di, di
   317 0000032D B90040                  	mov	cx, 16384
   318 00000330 F366A5                  	rep	movsd
   319                                  	
   320                                  	; Turn off the floppy drive motor
   321 00000333 BAF203                          mov     dx, 3F2h
   322 00000336 EE                              out     dx, al ; 0 ; 31/12/2013
   323                                  
   324                                  	; Enable access to memory above one megabyte
   325                                  L18:
   326 00000337 E464                    	in	al, 64h
   327 00000339 A802                    	test	al, 2
   328 0000033B 75FA                            jnz     short L18
   329 0000033D B0D1                    	mov	al, 0D1h	; Write output port
   330 0000033F E664                    	out	64h, al
   331                                  L19:
   332 00000341 E464                    	in	al, 64h
   333 00000343 A802                    	test	al, 2
   334 00000345 75FA                            jnz     short L19
   335 00000347 B0DF                    	mov	al, 0DFh	; Enable A20 line
   336 00000349 E660                    	out	60h, al
   337                                  ;L20:
   338                                  	;
   339                                  	; Load global descriptor table register
   340                                  
   341                                          ;mov     ax, cs
   342                                          ;mov     ds, ax
   343                                  
   344 0000034B 2E0F0116[1864]                  lgdt    [cs:gdtd]
   345                                  
   346 00000351 0F20C0                          mov     eax, cr0
   347                                  	; or 	eax, 1
   348 00000354 40                      	inc     ax
   349 00000355 0F22C0                  	mov     cr0, eax
   350                                  
   351                                  	; Jump to 32 bit code
   352                                  	
   353 00000358 66                      	db 66h 			; Prefix for 32-bit
   354 00000359 EA                      	db 0EAh 		; Opcode for far jump
   355 0000035A [60030000]              	dd StartPM 		; Offset to start, 32-bit
   356                                  				; (1000h:StartPM = StartPM + 10000h)
   357 0000035E 0800                    	dw KCODE		; This is the selector for CODE32_DESCRIPTOR,
   358                                  				; assuming that StartPM resides in code32
   359                                  
   360                                  ; 20/02/2017
   361                                  
   362                                  
   363                                  [BITS 32] 
   364                                  
   365                                  StartPM:
   366                                  	; Kernel Base Address = 0 ; 30/12/2013
   367 00000360 66B81000                	mov ax, KDATA           ; Save data segment identifier
   368 00000364 8ED8                            mov ds, ax              ; Move a valid data segment into DS register
   369 00000366 8EC0                           	mov es, ax              ; Move data segment into ES register
   370 00000368 8EE0                           	mov fs, ax              ; Move data segment into FS register
   371 0000036A 8EE8                          	mov gs, ax              ; Move data segment into GS register
   372 0000036C 8ED0                            mov ss, ax              ; Move data segment into SS register
   373 0000036E BC00000900                      mov esp, 90000h         ; Move the stack pointer to 090000h
   374                                  
   375                                  clear_bss: ; Clear uninitialized data area
   376                                  	; 11/03/2015
   377 00000373 31C0                    	xor  eax, eax ; 0
   378 00000375 B9956D0000              	mov  ecx, (bss_end - bss_start)/4
   379                                  	;shr  ecx, 2 ; bss section is already aligned for double words
   380 0000037A BF[925B0100]            	mov  edi, bss_start	
   381 0000037F F3AB                    	rep  stosd  		
   382                                  
   383                                  memory_init:
   384                                  	; Initialize memory allocation table and page tables
   385                                  	; 16/11/2014
   386                                  	; 15/11/2014
   387                                  	; 07/11/2014
   388                                  	; 06/11/2014
   389                                  	; 05/11/2014
   390                                  	; 04/11/2014
   391                                  	; 31/10/2014 (Retro UNIX 386 v1 - Beginning) 
   392                                  	;
   393                                  ;	xor	eax, eax
   394                                  ;	xor 	ecx, ecx
   395 00000381 B108                    	mov	cl, 8
   396 00000383 BF00001000              	mov	edi, MEM_ALLOC_TBL	
   397 00000388 F3AB                    	rep	stosd		   ; clear Memory Allocation Table
   398                                  				   ; for the first 1 MB memory
   399                                  	;
   400 0000038A 668B0D[A6640000]        	mov	cx, [mem_1m_1k]	   ; Number of contiguous KB between
   401                                  				   ; 1 and 16 MB, max. 3C00h = 15 MB.
   402 00000391 66C1E902                	shr	cx, 2		   ; convert 1 KB count to 4 KB count
   403 00000395 890D[885E0100]          	mov	[free_pages], ecx
   404 0000039B 668B15[A8640000]        	mov	dx, [mem_16m_64k]  ; Number of contiguous 64 KB blocks
   405                                  				   ; between 16 MB and 4 GB.	
   406 000003A2 6609D2                  	or	dx, dx
   407 000003A5 7413                    	jz	short mi_0
   408                                  	;
   409 000003A7 6689D0                  	mov	ax, dx
   410 000003AA C1E004                  	shl	eax, 4		   ; 64 KB -> 4 KB (page count)
   411 000003AD 0105[885E0100]          	add	[free_pages], eax
   412 000003B3 0500100000              	add	eax, 4096	   ; 16 MB = 4096 pages
   413 000003B8 EB07                    	jmp	short mi_1
   414                                  mi_0:
   415 000003BA 6689C8                  	mov	ax, cx
   416 000003BD 66050001                	add	ax, 256		   ; add 256 pages for the first 1 MB		 
   417                                  mi_1:
   418 000003C1 A3[845E0100]            	mov	[memory_size], eax ; Total available memory in pages
   419                                  				   ; 1 alloc. tbl. bit = 1 memory page
   420                                  				   ; 32 allocation bits = 32 mem. pages   
   421                                  	;
   422 000003C6 05FF7F0000              	add	eax, 32767	   ; 32768 memory pages per 1 M.A.T. page 	
   423 000003CB C1E80F                  	shr	eax, 15		   ; ((32768 * x) + y) pages (y < 32768)
   424                                  				   ;  --> x + 1 M.A.T. pages, if y > 0
   425                                  				   ;  --> x M.A.T. pages, if y = 0
   426 000003CE 66A3[985E0100]          	mov	[mat_size], ax	   ; Memory Alloc. Table Size in pages		
   427 000003D4 C1E00C                  	shl	eax, 12		   ; 1 M.A.T. page = 4096 bytes
   428                                  	;			   ; Max. 32 M.A.T. pages (4 GB memory)
   429 000003D7 89C3                    	mov	ebx, eax	   ; M.A.T. size in bytes
   430                                  	; Set/Calculate Kernel's Page Directory Address
   431 000003D9 81C300001000            	add	ebx, MEM_ALLOC_TBL
   432 000003DF 891D[805E0100]          	mov	[k_page_dir], ebx  ; Kernel's Page Directory address
   433                                  				   ; just after the last M.A.T. page
   434                                  	;
   435 000003E5 83E804                  	sub	eax, 4		   ; convert M.A.T. size to offset value
   436 000003E8 A3[905E0100]            	mov	[last_page], eax   ; last page ofset in the M.A.T.
   437                                  	;			   ; (allocation status search must be 
   438                                  				   ; stopped after here)	
   439 000003ED 31C0                    	xor	eax, eax
   440 000003EF 48                      	dec	eax		   ; FFFFFFFFh (set all bits to 1)	
   441 000003F0 6651                    	push	cx
   442 000003F2 C1E905                  	shr	ecx, 5		   ; convert 1 - 16 MB page count to 
   443                                  				   ; count of 32 allocation bits
   444 000003F5 F3AB                    	rep	stosd
   445 000003F7 6659                    	pop	cx
   446 000003F9 40                      	inc	eax		   ; 0	
   447 000003FA 80E11F                  	and	cl, 31		   ; remain bits
   448 000003FD 7412                    	jz	short mi_4
   449 000003FF 8907                    	mov	[edi], eax	   ; reset	
   450                                  mi_2:
   451 00000401 0FAB07                  	bts	[edi], eax	   ; 06/11/2014		
   452 00000404 FEC9                    	dec	cl
   453 00000406 7404                    	jz	short mi_3
   454 00000408 FEC0                    	inc	al
   455 0000040A EBF5                    	jmp	short mi_2
   456                                  mi_3:
   457 0000040C 28C0                    	sub	al, al	   	   ; 0
   458 0000040E 83C704                  	add	edi, 4		   ; 15/11/2014
   459                                  mi_4:
   460 00000411 6609D2                  	or	dx, dx		  ; check 16M to 4G memory space	
   461 00000414 7421                    	jz	short mi_6	  ; max. 16 MB memory, no more...
   462                                  	;	
   463 00000416 B900021000              	mov	ecx, MEM_ALLOC_TBL + 512 ; End of first 16 MB memory
   464                                  	;	
   465 0000041B 29F9                    	sub	ecx, edi	  ; displacement (to end of 16 MB)
   466 0000041D 7406                    	jz	short mi_5	  ; jump if EDI points to 
   467                                  				  ;         end of first 16 MB	
   468 0000041F D1E9                    	shr	ecx, 1		  ; convert to dword count
   469 00000421 D1E9                    	shr	ecx, 1		  ; (shift 2 bits right) 
   470 00000423 F3AB                    	rep 	stosd		  ; reset all bits for reserved pages
   471                                  				  ; (memory hole under 16 MB)
   472                                  mi_5:
   473 00000425 6689D1                  	mov	cx, dx		  ; count of 64 KB memory blocks
   474 00000428 D1E9                    	shr	ecx, 1		  ; 1 alloc. dword per 128 KB memory
   475 0000042A 9C                      	pushf			  ; 16/11/2014		
   476 0000042B 48                      	dec	eax		  ; FFFFFFFFh (set all bits to 1)
   477 0000042C F3AB                    	rep	stosd
   478 0000042E 40                      	inc	eax		  ; 0
   479 0000042F 9D                      	popf			  ; 16/11/2014
   480 00000430 7305                    	jnc	short mi_6
   481 00000432 6648                    	dec	ax		  ; eax = 0000FFFFh
   482 00000434 AB                      	stosd
   483 00000435 6640                    	inc	ax		  ; 0		
   484                                  mi_6:
   485 00000437 39DF                    	cmp	edi, ebx	  ; check if EDI points to 	
   486 00000439 730A                    	jnb	short mi_7	  ; end of memory allocation table
   487                                  	;			  ; (>= MEM_ALLOC_TBL + 4906) 
   488 0000043B 89D9                    	mov	ecx, ebx	  ; end of memory allocation table
   489 0000043D 29F9                    	sub	ecx, edi	  ; convert displacement/offset
   490 0000043F D1E9                    	shr	ecx, 1		  ; to dword count 	 		
   491 00000441 D1E9                    	shr	ecx, 1		  ; (shift 2 bits right) 
   492 00000443 F3AB                    	rep 	stosd		  ; reset all remain M.A.T. bits
   493                                  mi_7:
   494                                  	; Reset M.A.T. bits in M.A.T. (allocate M.A.T. pages)
   495 00000445 BA00001000              	mov	edx, MEM_ALLOC_TBL
   496                                  	;sub	ebx, edx	  ; Mem. Alloc. Tbl. size in bytes
   497                                  	;shr	ebx, 12		  ; Mem. Alloc. Tbl. size in pages	
   498 0000044A 668B0D[985E0100]        	mov	cx, [mat_size]	  ; Mem. Alloc. Tbl. size in pages
   499 00000451 89D7                    	mov	edi, edx
   500 00000453 C1EF0F                  	shr	edi, 15		  ; convert M.A.T. address to
   501                                  				  ; byte offset in M.A.T.
   502                                  				  ; (1 M.A.T. byte points to 
   503                                  				  ;	      32768 bytes)
   504                                  				  ; Note: MEM_ALLOC_TBL address 
   505                                  				  ; must be aligned on 128 KB 
   506                                  				  ; boundary!
   507 00000456 01D7                    	add	edi, edx	  ; points to M.A.T.'s itself	
   508                                  	; eax = 0
   509 00000458 290D[885E0100]          	sub	[free_pages], ecx ; 07/11/2014
   510                                  mi_8:
   511 0000045E 0FB307                  	btr	[edi], eax	  ; clear bit 0 to bit x (1 to 31)
   512                                  	;dec	bl
   513 00000461 FEC9                    	dec	cl
   514 00000463 7404                    	jz	short mi_9
   515 00000465 FEC0                    	inc	al
   516 00000467 EBF5                    	jmp	short mi_8
   517                                  mi_9:
   518                                  	;
   519                                  	; Reset Kernel's Page Dir. and Page Table bits in M.A.T.
   520                                  	;		(allocate pages for system page tables)
   521                                  
   522                                  	; edx = MEM_ALLOC_TBL
   523 00000469 8B0D[845E0100]          	mov	ecx, [memory_size] ; memory size in pages (PTEs)
   524 0000046F 81C1FF030000            	add	ecx, 1023	 ; round up (1024 PTEs per table)	 	
   525 00000475 C1E90A                  	shr	ecx, 10		 ; convert memory page count to 
   526                                  				 ; page table count (PDE count)
   527                                  	;
   528 00000478 51                      	push	ecx		 ; (**) PDE count (<= 1024)
   529                                  	;
   530 00000479 41                      	inc	ecx		 ; +1 for kernel page directory	
   531                                  	;
   532 0000047A 290D[885E0100]          	sub	[free_pages], ecx ; 07/11/2014
   533                                  	;
   534 00000480 8B35[805E0100]          	mov	esi, [k_page_dir] ; Kernel's Page Directory address
   535 00000486 C1EE0C                  	shr	esi, 12		 ; convert to page number
   536                                  mi_10:
   537 00000489 89F0                    	mov	eax, esi	 ; allocation bit offset		 
   538 0000048B 89C3                    	mov	ebx, eax
   539 0000048D C1EB03                  	shr	ebx, 3		 ; convert to alloc. byte offset
   540 00000490 80E3FC                  	and	bl,  0FCh	 ; clear bit 0 and bit 1
   541                                  				 ;   to align on dword boundary
   542 00000493 83E01F                  	and	eax, 31		 ; set allocation bit position 
   543                                  				 ;  (bit 0 to bit 31)
   544                                  	;
   545 00000496 01D3                    	add	ebx, edx	 ; offset in M.A.T. + M.A.T. address 
   546                                  	;
   547 00000498 0FB303                  	btr 	[ebx], eax	 ; reset relevant bit (0 to 31)
   548                                  	;
   549 0000049B 46                      	inc	esi		 ; next page table
   550 0000049C E2EB                    	loop	mi_10		 ; allocate next kernel page table 
   551                                  				 ; (ecx = page table count + 1)		
   552                                  	;
   553 0000049E 59                      	pop	ecx		 ; (**) PDE count (= pg. tbl. count)
   554                                  	;
   555                                  	; Initialize Kernel Page Directory and Kernel Page Tables
   556                                  	;
   557                                  	; Initialize Kernel's Page Directory
   558 0000049F 8B3D[805E0100]          	mov	edi, [k_page_dir]
   559 000004A5 89F8                    	mov	eax, edi
   560 000004A7 0C03                    	or	al, PDE_A_PRESENT + PDE_A_WRITE
   561                                  		     	      ; supervisor + read&write + present
   562 000004A9 89CA                    	mov	edx, ecx 	; (**) PDE count (= pg. tbl. count)	
   563                                  mi_11:
   564 000004AB 0500100000              	add	eax, 4096	; Add page size (PGSZ)
   565                                  			        ; EAX points to next page table
   566 000004B0 AB                      	stosd
   567 000004B1 E2F8                    	loop	mi_11
   568 000004B3 29C0                    	sub	eax, eax	; Empty PDE
   569 000004B5 66B90004                	mov	cx, 1024	; Entry count (PGSZ/4)
   570 000004B9 29D1                    	sub	ecx, edx
   571 000004BB 7402                    	jz	short mi_12
   572 000004BD F3AB                    	rep	stosd 		; clear remain (empty) PDEs
   573                                  	;
   574                                  	; Initialization of Kernel's Page Directory is OK, here.
   575                                  mi_12:
   576                                  	; Initialize Kernel's Page Tables
   577                                  	;
   578                                  	; (EDI points to address of page table 0)
   579                                  	; eax = 0
   580 000004BF 8B0D[845E0100]          	mov	ecx, [memory_size] ; memory size in pages
   581 000004C5 89CA                    	mov	edx, ecx	; (***)
   582 000004C7 B003                    	mov	al, PTE_A_PRESENT + PTE_A_WRITE
   583                                  			     ; supervisor + read&write + present 	
   584                                  mi_13:
   585 000004C9 AB                      	stosd
   586 000004CA 0500100000              	add	eax, 4096	
   587 000004CF E2F8                    	loop	mi_13	
   588 000004D1 6681E2FF03              	and	dx, 1023	; (***)
   589 000004D6 740B                    	jz	short mi_14
   590 000004D8 66B90004                	mov	cx, 1024	
   591 000004DC 6629D1                  	sub	cx, dx		; from dx (<= 1023) to 1024
   592 000004DF 31C0                    	xor	eax, eax
   593 000004E1 F3AB                    	rep	stosd		; clear remain (empty) PTEs 
   594                                  				; of the last page table
   595                                  mi_14:
   596                                  	;  Initialization of Kernel's Page Tables is OK, here.
   597                                  	;
   598 000004E3 89F8                    	mov	eax, edi	; end of the last page table page
   599                                  			        ; (beginging of user space pages)
   600 000004E5 C1E80F                  	shr	eax, 15		; convert to M.A.T. byte offset
   601 000004E8 24FC                    	and	al, 0FCh	; clear bit 0 and bit 1 for
   602                                  				; aligning on dword boundary	
   603                                  	 
   604 000004EA A3[945E0100]            	mov	[first_page], eax
   605 000004EF A3[8C5E0100]            	mov	[next_page], eax ; The first free page pointer
   606                                  				 ; for user programs
   607                                  				 ; (Offset in Mem. Alloc. Tbl.)	
   608                                  	;
   609                                  	; Linear/FLAT (1 to 1) memory paging for the kernel is OK, here.
   610                                  	;
   611                                  	
   612                                  	; Enable paging
   613                                  	;
   614 000004F4 A1[805E0100]                    mov     eax, [k_page_dir]
   615 000004F9 0F22D8                  	mov	cr3, eax
   616 000004FC 0F20C0                  	mov	eax, cr0
   617 000004FF 0D00000080              	or	eax, 80000000h	; set paging bit (bit 31)
   618 00000504 0F22C0                  	mov	cr0, eax
   619                                          ;jmp    KCODE:StartPMP
   620                                  
   621 00000507 EA                      	db 0EAh 		; Opcode for far jump
   622 00000508 [0E050000]                      dd StartPMP		; 32 bit offset
   623 0000050C 0800                    	dw KCODE		; kernel code segment descriptor
   624                                  
   625                                  StartPMP:
   626                                  	; 06/11//2014
   627                                  	; Clear video page 0
   628                                  	;
   629                                  	; Temporary Code
   630                                  	;
   631 0000050E B9E8030000              	mov	ecx, 80*25/2
   632 00000513 BF00800B00              	mov	edi, 0B8000h
   633                                  	; 30/01/2016
   634                                  	;xor	eax, eax	; black background, black fore color
   635 00000518 B800070007              	mov	eax, 07000700h  ; black background, light gray fore color
   636 0000051D F3AB                    	rep	stosd
   637                                  	
   638                                  	; 19/08/2014
   639                                  	; Kernel Base Address = 0
   640                                  	; It is mapped to (physically) 0 in the page table.
   641                                  	; So, here is exactly 'StartPMP' address.
   642                                  
   643                                   	; 29/01/2016 (TRDOS 386 = TRDOS v2.0)
   644 0000051F BE[811F0100]            	mov	esi, starting_msg
   645                                  	;; 14/08/2015 (kernel version message will appear
   646                                  	;;	       when protected mode and paging is enabled)
   647 00000524 BF00800B00              	mov	edi, 0B8000h ; 27/08/2014
   648                                  	
   649                                  	; 30/11/2020
   650                                  	; 14/11/2020 (TRDOS 386 v2.0.3)
   651                                  	;cmp	byte [vbe3], 3 ; 03h
   652                                  	;jne	short pkv_1
   653                                  	;;mov	ah, 0Bh ; Black background, light cyan forecolor
   654                                  	;; Light red TRDOS 386 version text shows VBE3 is ready !
   655                                  	;mov	ah, 0Ch ; Black background, light red forecolor
   656                                  	;jmp	short pkv_2
   657                                  ;pkv_1:
   658 00000529 B40A                    	mov	ah, 0Ah ; Black background, light green forecolor
   659                                  ;pkv_2:
   660                                  	; 20/08/2014
   661 0000052B E891030000              	call	printk
   662                                  
   663                                  	; 'UNIX v7/x86' source code by Robert Nordier (1999)
   664                                  	; // Set IRQ offsets
   665                                  	;
   666                                  	;  Linux (v0.12) source code by Linus Torvalds (1991)
   667                                  	;
   668                                  					;; ICW1
   669 00000530 B011                    	mov	al, 11h			; Initialization sequence
   670 00000532 E620                    	out	20h, al			; 	8259A-1
   671                                  	; jmp 	$+2
   672 00000534 E6A0                    	out	0A0h, al		; 	8259A-2
   673                                  					;; ICW2
   674 00000536 B020                    	mov	al, 20h			; Start of hardware ints (20h)
   675 00000538 E621                    	out	21h, al			;	for 8259A-1
   676                                  	; jmp 	$+2
   677 0000053A B028                    	mov	al, 28h			; Start of hardware ints (28h)
   678 0000053C E6A1                    	out	0A1h, al		; 	for 8259A-2
   679                                  					;
   680 0000053E B004                    	mov	al, 04h			;; ICW3
   681 00000540 E621                    	out	21h, al			; 	IRQ2 of 8259A-1 (master)
   682                                  	; jmp 	$+2
   683 00000542 B002                    	mov	al, 02h			; 	is 8259A-2 (slave)
   684 00000544 E6A1                    	out	0A1h, al		;
   685                                  					;; ICW4
   686 00000546 B001                    	mov	al, 01h	 		;
   687 00000548 E621                    	out	21h, al			; 	8086 mode, normal EOI	
   688                                  	; jmp 	$+2
   689 0000054A E6A1                    	out	0A1h, al		;	for both chips.
   690                                  
   691                                  	;mov	al, 0FFh	; mask off all interrupts for now
   692                                  	;out	21h, al
   693                                  	;; jmp 	$+2
   694                                  	;out	0A1h, al
   695                                  
   696                                  	; 02/04/2015
   697                                  	; 26/03/2015 System call (INT 30h) modification
   698                                  	;  DPL = 3 (Interrupt service routine can be called from user mode)			
   699                                  	;
   700                                  	;; Linux (v0.12) source code by Linus Torvalds (1991)
   701                                  	;  setup_idt:
   702                                  	;
   703                                          ;; 16/02/2015
   704                                  	;;mov     dword [DISKETTE_INT], fdc_int ; IRQ 6 handler
   705                                  	; 21/08/2014 (timer_int)
   706 0000054C BE[441C0100]            	mov	esi, ilist
   707 00000551 8D3D[985B0100]          	lea	edi, [idt]
   708                                  	; 26/03/2015
   709 00000557 B930000000              	mov	ecx, 48		; 48 hardware interrupts (INT 0 to INT 2Fh)
   710                                  	; 02/04/2015
   711 0000055C BB00000800              	mov	ebx,  80000h
   712                                  rp_sidt1:
   713 00000561 AD                      	lodsd
   714 00000562 89C2                    	mov	edx, eax
   715 00000564 66BA008E                	mov	dx, 8E00h
   716 00000568 6689C3                  	mov	bx, ax
   717 0000056B 89D8                    	mov	eax, ebx	; /* selector = 0x0008 = cs */
   718                                         			        ; /* interrupt gate - dpl=0, present */
   719 0000056D AB                      	stosd	; selector & offset bits 0-15 	
   720 0000056E 89D0                    	mov	eax, edx
   721 00000570 AB                      	stosd	; attributes & offset bits 16-23
   722 00000571 E2EE                    	loop	rp_sidt1
   723                                  	; 15/04/2016
   724                                  	; TRDOS 386 (TRDOS v2.0) /// 32 sofware interrupts ///
   725                                  	;mov	cl, 16        ; 16 software interrupts (INT 30h to INT 3Fh)
   726 00000573 B120                    	mov	cl, 32	      ; 32 software interrupts (INT 30h to INT 4Fh)	
   727                                  rp_sidt2:
   728 00000575 AD                      	lodsd
   729 00000576 21C0                    	and	eax, eax
   730 00000578 7413                    	jz	short rp_sidt3
   731 0000057A 89C2                    	mov	edx, eax
   732 0000057C 66BA00EE                	mov	dx, 0EE00h	; P=1b/DPL=11b/01110b
   733 00000580 6689C3                  	mov	bx, ax
   734 00000583 89D8                    	mov	eax, ebx	; selector & offset bits 0-15 	
   735 00000585 AB                      	stosd
   736 00000586 89D0                    	mov	eax, edx
   737 00000588 AB                      	stosd
   738 00000589 E2EA                    	loop	rp_sidt2
   739 0000058B EB16                    	jmp	short sidt_OK
   740                                  rp_sidt3:
   741 0000058D B8[EE0C0000]            	mov	eax, ignore_int
   742 00000592 89C2                    	mov	edx, eax
   743 00000594 66BA00EE                	mov	dx, 0EE00h	; P=1b/DPL=11b/01110b
   744 00000598 6689C3                  	mov	bx, ax
   745 0000059B 89D8                    	mov	eax, ebx	; selector & offset bits 0-15 	
   746                                  rp_sidt4:
   747 0000059D AB                      	stosd
   748 0000059E 92                      	xchg	eax, edx
   749 0000059F AB                      	stosd
   750 000005A0 92                      	xchg	edx, eax
   751 000005A1 E2FA                    	loop	rp_sidt4
   752                                  sidt_OK: 
   753 000005A3 0F011D[1E640000]        	lidt 	[idtd]
   754                                  	;
   755                                  	; TSS descriptor setup ; 24/03/2015
   756 000005AA B8[185E0100]            	mov	eax, task_state_segment
   757 000005AF 66A3[CA630000]          	mov	[gdt_tss0], ax
   758 000005B5 C1C010                  	rol	eax, 16
   759 000005B8 A2[CC630000]            	mov	[gdt_tss1], al
   760 000005BD 8825[CF630000]          	mov	[gdt_tss2], ah
   761 000005C3 66C705[7E5E0100]68-     	mov	word [tss.IOPB], tss_end - task_state_segment
   761 000005CB 00                 
   762                                  		; 
   763                                  		; IO Map Base address (When this address points
   764                                  		; to end of the TSS, CPU does not use IO port 
   765                                  		; permission bit map for RING 3 IO permissions, 
   766                                  		; access to any IO ports in ring 3 will be forbidden.)
   767                                   		;
   768                                  	;mov	[tss.esp0], esp ; TSS offset 4
   769                                  	;mov	word [tss.ss0], KDATA ; TSS offset 8 (SS)
   770 000005CC 66B82800                   	mov	ax, TSS  ; It is needed when an interrupt 
   771                                  			 ; occurs (or a system call -software INT- is requested)
   772                                  			 ; while cpu running in ring 3 (in user mode).				
   773                                  			 ; (Kernel stack pointer and segment will be loaded
   774                                  			 ; from offset 4 and 8 of the TSS, by the CPU.)	 
   775 000005D0 0F00D8                  	ltr	ax  ; Load task register
   776                                  	;
   777                                  esp0_set0:
   778                                  	; 30/07/2015
   779 000005D3 8B0D[845E0100]          	mov 	ecx, [memory_size] ; memory size in pages
   780 000005D9 C1E10C                  	shl 	ecx, 12 ; convert page count to byte count
   781 000005DC 81F900004000            	cmp	ecx, CORE ; beginning of user's memory space (400000h)
   782                                  			  ; (kernel mode virtual address)
   783 000005E2 7605                    	jna	short esp0_set1
   784                                  	;
   785                                  	; If available memory > CORE (end of the 1st 4 MB)
   786                                  	; set stack pointer to CORE
   787                                  	;(Because, PDE 0 is reserved for kernel space in user's page directory)
   788                                  	;(PDE 0 points to page table of the 1st 4 MB virtual address space)
   789 000005E4 B900004000              	mov	ecx, CORE
   790                                  esp0_set1:
   791 000005E9 89CC                    	mov	esp, ecx ; top of kernel stack (**tss.esp0**)
   792                                  esp0_set_ok:
   793                                  	; 30/07/2015 (**tss.esp0**) 
   794 000005EB 8925[1C5E0100]          	mov	[tss.esp0], esp
   795 000005F1 66C705[205E0100]10-             mov     word [tss.ss0], KDATA
   795 000005F9 00                 
   796                                  	; 14/08/2015
   797                                  	; 10/11/2014 (Retro UNIX 386 v1 - Erdogan Tan)
   798                                  	;
   799                                  	;cli	; Disable interrupts (for CPU)
   800                                  	;    (CPU will not handle hardware interrupts, except NMI!)
   801                                  	;
   802 000005FA 30C0                    	xor	al, al		; Enable all hardware interrupts!
   803 000005FC E621                    	out	21h, al		; (IBM PC-AT compatibility)
   804 000005FE EB00                    	jmp 	$+2		; (All conventional PC-AT hardware
   805 00000600 E6A1                    	out	0A1h, al	;  interrupts will be in use.)	
   806                                  				; (Even if related hardware component
   807                                  				;  does not exist!)
   808                                  	; Enable NMI 
   809 00000602 B07F                    	mov	al, 7Fh		; Clear bit 7 to enable NMI (again)
   810 00000604 E670                    	out  	70h, al
   811                                  	; 23/02/2015
   812 00000606 90                      	nop
   813 00000607 E471                    	in	al, 71h		; read in 71h just after writing out to 70h
   814                                  				; for preventing unknown state (!?)
   815                                  	;
   816                                  	; Only a NMI can occur here... (Before a 'STI' instruction)
   817                                  	;
   818                                  	; 02/09/2014
   819 00000609 6631DB                  	xor	bx, bx
   820 0000060C 66BA0002                	mov	dx, 0200h	; Row 2, column 0  ; 07/03/2015
   821 00000610 E85E1B0000              	call	_set_cpos	; 24/01/2016
   822                                  
   823                                  	; 14/11/2020 (TRDOS 386 v2.0.3)
   824                                  	; Check VBE3 protected mode interface/feature(s)
   825                                  
   826                                  	;cmp	byte [vbe3], 3 ; 03h
   827                                  	;jne	short display_mem_info
   828                                  	
   829                                  	; 30/11/2020 - test 16 bit pm selectors (OK)
   830                                  	;jmp	vbe3pminit
   831                                  
   832                                  	; 20/11/2020
   833 00000615 803D[CB080000]02        	cmp	byte [vbe3], 2 ; 02h
   834 0000061C 770B                    	ja	short vbe3_pmid_chk
   835 0000061E 0F82A6010000            	jb	display_mem_info
   836 00000624 E9D5010000              	jmp	check_boch_plex86_vbe
   837                                  vbe3_pmid_chk:	
   838 00000629 B9EA7F0000              	mov	ecx, 32768 - (20+2) ; 32766 - PMInfoBlockSize
   839 0000062E BE02000C00              	mov	esi, 0C0002h ; 1st word of the video bios rom is 0AA55h
   840                                  chk_pmi_sign:
   841                                  	;mov	eax, [esi] 
   842                                  	;cmp	eax, 'PMID'
   843                                  	; 30/11/2020
   844                                  	;cmp	al, 'P'
   845                                  	;jne	short chk_pmi_sign_next
   846 00000633 813E504D4944            	cmp	dword [esi], 'PMID'
   847                                  	;je	short display_vbios_product_name
   848 00000639 740E                    	je	short verify_pmib_chksum ; 15/11/2020
   849                                  ;chk_pmi_sign_next:
   850 0000063B 46                      	inc	esi  ; inc si
   851 0000063C E2F5                    	loop	chk_pmi_sign
   852                                  
   853                                  not_valid_pmib:
   854 0000063E FE0D[CB080000]          	dec	byte [vbe3] ; 2 = VBE2 compatible 
   855                                  			    ; (vbe3 feature is defective in this vbios)
   856 00000644 E981010000              	jmp	display_mem_info
   857                                  
   858                                  verify_pmib_chksum:
   859                                  	; 15/11/2020
   860 00000649 31C0                    	xor	eax, eax
   861                                  	;mov	ecx, eax 
   862                                  	;mov	cl, 20
   863 0000064B 66B91400                	mov	cx, 20 ; 30/11/2020
   864 0000064F 56                      	push	esi
   865                                  pmib_sum_bytes:
   866 00000650 AC                      	lodsb
   867 00000651 00C4                    	add	ah, al
   868 00000653 E2FB                    	loop	pmib_sum_bytes
   869 00000655 5E                      	pop	esi
   870 00000656 08E4                    	or	ah, ah
   871 00000658 75E4                    	jnz	short not_valid_pmib ; AH must be 0
   872                                  
   873                                  display_vbios_product_name: ; 14/11/2020
   874                                  
   875                                  	; ESI points to 'PMID' (0C0000h + 'PMID' offset)
   876                                  
   877                                  	; 15/11/2020
   878                                  	;mov	[pmid_addr], si	; PMInfoBlock offset
   879                                  	;		; (in VGA bios, 0C0000h + offset)
   880                                  	; 30/11/2020
   881 0000065A 89F7                    	mov	edi, esi
   882                                  
   883                                  	;mov	esi, [VBE3INFOBLOCK+22] ; 097E00h + 16h
   884                                  	;		; OemVendorNamePtr (seg16:off16)
   885 0000065C 8B35067E0900            	mov	esi, [VBE3INFOBLOCK+6] ; 097E00h + 06h
   886                                  			; OemStringPtr (seg16:off16)
   887 00000662 30C0                    	xor	al, al  ; eax = 0
   888 00000664 6696                    	xchg	ax, si	; ax = offset, si = 0
   889 00000666 C1EE0C                  	shr	esi, 12 ; (to convert segment to base addr)
   890 00000669 6601C6                  	add	si, ax  ; esi has an address < 1 MB limit
   891                                  			; (OemVendorName is in VBE3INFOBLOCK)
   892                                  			; Example: 
   893                                  			; TRDOS 386 v2.0.3 VESA VBE3 protected mode
   894                                  			; interface development reference is ...
   895                                  			; NVIDIA GeForce FX5500 VGA BIOS -C000h:029Ch-
   896                                  			; Version 4.34.20.54.00 -C000h:02EDh- 	  
   897                                  			; ((OemString is 'NVIDIA'))
   898                                  			; ((OemVendorName is 'NVIDIA Corporation'))
   899                                  			; ((OemProductName is 'NV34 Board - p162-1nz))
   900                                  
   901                                  	;mov	ah, 0Eh ; Black background, yellow forecolor
   902                                  	; 30/11/2020
   903 0000066C B40C                    	mov	ah, 0Ch ; Black background, light red forecolor
   904                                  
   905 0000066E E851330000              	call	print_kmsg
   906                                  
   907                                  	;mov	ah, 07h
   908                                  
   909 00000673 BE[265B0100]            	mov	esi, vesa_vbe3_bios_msg
   910                                  	;call	print_kmsg
   911 00000678 E84D330000              	call	pkmsg_loop ; 30/11/2020
   912                                  
   913                                  	; 30/11/2020
   914                                  	; 29/11/2020 - TRDOS 386 v2.0.3
   915                                  
   916                                  struc PMInfo  ;  VESA VBE3 PMInfoBlock ('PMID' block)
   917                                  
   918 00000000 <res 00000004>           .Signature:	resb 4  ; db 'PMID' ; PM Info Block Signature
   919 00000004 <res 00000002>           .EntryPoint:	resw 1	; Offset of PM entry point within BIOS
   920 00000006 <res 00000002>           .PMInitialize: resw 1	; Offset of PM initialization entry point
   921 00000008 <res 00000002>           .BIOSDataSel:	resw 1 	; Selector to BIOS data area emulation block
   922 0000000A <res 00000002>           .A0000Sel:	resw 1	; Selector to access A0000h physical mem
   923 0000000C <res 00000002>           .B0000Sel:	resw 1  ; Selector to access B0000h physical mem
   924 0000000E <res 00000002>           .B8000Sel:	resw 1	; Selector to access B8000h physical mem
   925 00000010 <res 00000002>           .CodeSegSel:	resw 1	; Selector to access code segment as data
   926 00000012 <res 00000001>           .InProtectMode: resb 1 ; Set to 1 when in protected mode
   927 00000013 <res 00000001>           .Checksum:	resb 1	; Checksum byte for structure
   928                                   .size:
   929                                  
   930                                  endstruc
   931                                  
   932                                  	; 29/11/2020
   933                                  vbe3pminit:
   934                                  	; 30/11/2020
   935                                  	;cmp	byte [vbe3], 3 ; is VESA VBE3 PMI ready ?
   936                                  	;jne	short di4
   937                                  
   938                                  	; Allocate 64KB contiguous (kernel) memory block
   939 0000067D 31C0                    	xor	eax, eax
   940 0000067F B900000100              	mov	ecx, 65536
   941 00000684 E806550000              	call	allocate_memory_block
   942                                  	;jc	short di4
   943 00000689 0F8234010000            	jc	di0 ; 30/11/2020	
   944                                  
   945                                  	; of course this block must be in the 1st 16MB
   946                                  	; because vbe3 pmi segments will be 16 bit segments
   947                                  	; (80286 type segment descriptors in GDT)
   948                                  	
   949 0000068F A3[A0110300]            	mov	[vbe3bios_addr], eax
   950                                  
   951                                  	; set [pmid_addr] to the new location
   952 00000694 BE00000C00              	mov	esi, 0C0000h
   953                                  	; 30/11/2020
   954 00000699 29F7                    	sub	edi, esi ; izolate offset
   955 0000069B 01C7                    	add	edi, eax ; new address
   956 0000069D 893D[CD080000]          	mov	[pmid_addr], edi ; new 'PMID' location	
   957                                  
   958                                  	; Move VIDEO BIOS from 0C0000h to EAX
   959 000006A3 B900400000              	mov	ecx, 65536/4 
   960 000006A8 89C7                    	mov	edi, eax ; 30/11/2020
   961 000006AA F3A5                    	rep	movsd
   962                                  
   963                                  	; set vbe3 segment selectors
   964                                  
   965                                  	; VBE3CS (VESA VBE3 video bios code segment)
   966 000006AC BF[D2630000]            	mov	edi, _vbe3_CS+2 ; base address bits 0..15
   967 000006B1 66AB                    	stosw	; edi = _vbe3_CS+4
   968 000006B3 C1C810                  	ror	eax, 16
   969 000006B6 8807                    	mov	[edi], al ; base address, bits 16..23
   970                                  
   971                                  	; VBE3DS ('CodeSegSel' in PMInfoBlock)
   972 000006B8 BF[FC630000]            	mov	edi, _vbe3_DS+4 ; base addr bits 16..23
   973 000006BD 8807                    	mov	[edi], al 
   974 000006BF C1C010                  	rol	eax, 16
   975 000006C2 668947FE                	mov	[edi-2], ax ; base address, bits 0..15
   976                                  
   977                                  	; VBE3BDS (BIOSDataSel in PMInfoBlock)
   978 000006C6 BF[DA630000]            	mov	edi, _vbe3_BDS+2 ; base addr bits 0..15
   979 000006CB B800700900              	mov	eax, VBE3BIOSDATABLOCK ; 1536 bytes
   980 000006D0 66AB                    	stosw	; edi = _vbe3_DS+4
   981 000006D2 C1E810                  	shr	eax, 16
   982 000006D5 8807                    	mov	[edi], al ; base address, bits 16..23
   983                                  
   984                                  	; VBE3SS (1024 bytes)
   985 000006D7 BF[02640000]            	mov	edi, _vbe3_SS+2 ; base addr bits 0..15
   986 000006DC B800600900              	mov	eax, VBE3STACKADDR ; size = 1024 bytes
   987 000006E1 66AB                    	stosw	; edi = _vbe3_SS+4
   988 000006E3 C1E810                  	shr	eax, 16
   989 000006E6 8807                    	mov	[edi], al ; base address, bits 16..23
   990                                  
   991                                  	; stack pointer (esp) will be set to 1020
   992                                  	; (before VBE3 PMI call)
   993                                  
   994                                  	; VBE3ES (max: 2048 bytes)
   995 000006E8 BF[0A640000]            	mov	edi, _vbe3_ES+2 ; base addr bits 0..15
   996 000006ED B800760900              	mov	eax, VBE3SAVERESTOREBLOCK
   997 000006F2 66AB                    	stosw	; edi = _vbe3_SS+4
   998 000006F4 C1E810                  	shr	eax, 16
   999 000006F7 8807                    	mov	[edi], al ; base address, bits 16..23 	
  1000                                  
  1001                                  	;Note: low word of _VBE3_ES base address will be
  1002                                  	;	set -again- by VBE3 PMI caller routine 
  1003                                  
  1004                                  	; set pmi32 (as VBE3 PMI is ready)
  1005 000006F9 FE05[9C110300]          	inc	byte [pmi32] ; = 1 
  1006                                  
  1007                                  	; KCODE16 (set PMI far return segment)
  1008 000006FF BF[12640000]            	mov	edi, _16bit_CS+2 ; base addr bits 0..15
  1009 00000704 B8[8C070000]            	mov	eax, pminit_return_addr16
  1010 00000709 66AB                    	stosw	; edi = _vbe3_SS+4
  1011 0000070B C1E810                  	shr	eax, 16
  1012 0000070E 8807                    	mov	[edi], al ; base address, bits 16..23 
  1013                                  
  1014                                  	; 30/11/2020
  1015                                  	; clear mem from VBE3 BIOS data area emu block
  1016                                  	; to end of vbe3 buffers
  1017                                  
  1018 00000710 BF007E0900              	mov	edi, VBE3INFOBLOCK ; 97E00h
  1019 00000715 66B98003                	mov	cx, (VBE3INFOBLOCK-VBE3BIOSDATABLOCK)/4
  1020                                  		; ecx = 3584/4 double words
  1021                                  	;xor	eax, eax
  1022 00000719 30C0                    	xor	al, al
  1023 0000071B F3AB                    	rep	stosd
  1024                                  
  1025                                  	; Filling PMInfoBlock selector fields
  1026 0000071D 8B3D[CD080000]          	mov	edi, [pmid_addr]
  1027 00000723 66C747083800            	mov	word [edi+PMInfo.BIOSDataSel], VBE3BDS
  1028 00000729 66C7470A4000            	mov	word [edi+PMInfo.A0000Sel], VBE3A000
  1029 0000072F 66C7470C4800            	mov	word [edi+PMInfo.B0000Sel], VBE3B000
  1030 00000735 66C7470E5000            	mov	word [edi+PMInfo.B8000Sel], VBE3B800	
  1031 0000073B 66C747105800            	mov	word [edi+PMInfo.CodeSegSel], VBE3DS
  1032 00000741 C6471201                	mov	byte [edi+PMInfo.InProtectMode], 1
  1033                                  
  1034                                  	; Calculate and write checksum byte
  1035 00000745 89FE                    	mov	esi, edi
  1036 00000747 B113                    	mov	cl, PMInfo.size - 1
  1037                                  	;xor	ah, ah
  1038                                  pmid_chksum:
  1039 00000749 AC                      	lodsb	
  1040 0000074A 00C4                    	add	ah, al
  1041 0000074C E2FB                    	loop	pmid_chksum
  1042 0000074E F6DC                    	neg	ah ; 1 -> 255, 255 -> 1
  1043 00000750 8826                    	mov	byte [esi], ah  ; checksum
  1044                                  
  1045                                  	; far call PM initialization
  1046                                  	; (VBE3 video bios will return via 'retf')
  1047                                  
  1048 00000752 668B4706                	mov	ax, [edi+PMInfo.PMInitialize]
  1049                                  	; 30/11/2020
  1050 00000756 C1E010                  	shl	eax, 16 ; save entry address in hw
  1051                                  	; ax = 0 
  1052                                  
  1053 00000759 68[AF070000]            	push	pminit_ok ; normal, near return address
  1054                                  
  1055                                  	; 30/11/2020
  1056                                  _VBE3PMI_fcall:
  1057                                  	; ax = function, hw of eax = entry address
  1058 0000075E 9C                      	pushfd	; save 32 bit flags
  1059 0000075F 56                      	push	esi ; *
  1060 00000760 55                      	push	ebp ; **
  1061                                  
  1062 00000761 89E5                    	mov	ebp, esp ; save 32 bit stack point
  1063                                  
  1064                                  	; set stack for iretd
  1065 00000763 89C6                    	mov	esi, eax
  1066                                  
  1067                                  	;cli
  1068                                  
  1069                                  	; Disable interrupts (clear interrupt flag)
  1070                                  	; Reset Interrupt MASK Registers (Master&Slave)
  1071 00000765 B0FF                    	mov	al, 0FFh	; mask off all interrupts
  1072 00000767 E621                    	out	21h, al		; on master PIC (8259)
  1073 00000769 EB00                    	jmp 	$+2  ; (delay)
  1074 0000076B E6A1                    	out	0A1h, al	; on slave PIC (8259)
  1075                                  
  1076 0000076D 66B86000                	mov	ax, VBE3SS
  1077 00000771 8ED0                    	mov	ss, ax
  1078 00000773 BCFC030000              	mov	esp, 1020 ; 30/11/2020
  1079                                  
  1080 00000778 C1E810                  	shr	eax, 16	; now, entry address is in lw
  1081                                  
  1082                                  	; 30/11/2020 - 16 bit pm selector test (OK)
  1083                                  	; (32 bit stack push/pop & retf with 32 bit code segment)
  1084                                  	; (16 bit stack push/pop with 16 bit code segment)
  1085                                  	
  1086                                  	; return
  1087                                  	;push	KCODE16
  1088                                  	;push	0 ; 30/11/2020 (pminit_return_addr16)
  1089                                  
  1090                                  	; 30/11/2020 (16 bit stack during retf from video bios)
  1091 0000077B C7042400007000          	mov	dword [esp], KCODE16 << 16
  1092                                  				; ip = 0, cs = KCODE16 
  1093                                  
  1094                                  	; 30/11/2020 (32 bit stack during retf from kernel)
  1095                                  	; far jump/call via retf
  1096 00000782 6A30                    	push	VBE3CS ; VBE3 video bios's code segment
  1097 00000784 50                      	push	eax ; PMInitialize or EntryPoint
  1098                                  
  1099 00000785 6689F0                  	mov	ax, si ; restore function
  1100 00000788 31F6                    	xor	esi, esi
  1101                                  	
  1102 0000078A CB                      	retf 	; far return (to 16 bit code segment) 		
  1103                                  
  1104 0000078B 90                      	align 2	
  1105                                  
  1106                                  pminit_return_addr16:
  1107                                  
  1108                                  	; 16 bit pm selector test (OK) - 30/11/2020
  1109                                  	;mov	ax, VBE3B800
  1110                                  	;mov	es, ax
  1111                                  	;xor	edi, edi
  1112                                  	;mov	al, 'P'
  1113                                  	;mov	ah, 4Eh
  1114                                  	;stosw
  1115                                  	;mov	al, 'M'
  1116                                  	;stosw
  1117                                  	;mov	al, '1'
  1118                                  	;stosw	
  1119                                  	;mov	al, '6'
  1120                                  	;stosw
  1121                                  	;mov	al, 'b'
  1122                                  	;stosw	
  1123                                  	;mov	al, 'i'
  1124                                  	;stosw
  1125                                  	;mov	al, 't'
  1126                                  	;stosw	
  1127                                  ;here_iloop:
  1128                                  	;hlt
  1129                                  	;jmp	short here_iloop	
  1130                                  
  1131                                  	; 30/11/2020
  1132 0000078C 66                      	db	66h 		     ; Prefix for 32-bit
  1133 0000078D EA                      	db	0EAh 		     ; Opcode for far jump
  1134 0000078E [94070000]              	dd	pminit_return_addr32 ; 32 bit Offset
  1135 00000792 0800                    	dw	KCODE		     ; 32 bit code segment
  1136                                  
  1137                                  pminit_return_addr32:
  1138                                  	; restore 32 bit kernel selectors and 32 bit stack addr
  1139 00000794 BE10000000              	mov	esi, KDATA
  1140 00000799 8EDE                    	mov	ds, si
  1141 0000079B 8EC6                    	mov	es, si
  1142 0000079D 8ED6                    	mov	ss, si
  1143 0000079F 89EC                    	mov	esp, ebp  ; top of stack = iretd return addr
  1144                                  
  1145 000007A1 5D                      	pop	ebp ; **
  1146 000007A2 5E                      	pop	esi ; *
  1147 000007A3 9D                      	popfd	; restore 32 bit flags
  1148                                  
  1149                                  	; enable interrupts
  1150                                  
  1151 000007A4 FA                      	cli
  1152                                  
  1153 000007A5 30C0                    	xor	al, al	   ; Enable all hardware interrupts!
  1154 000007A7 E621                    	out	21h, al	   ; (IBM PC-AT compatibility)
  1155 000007A9 EB00                    	jmp 	$+2	   ; (All conventional PC-AT hardware
  1156 000007AB E6A1                    	out	0A1h, al   ;  interrupts will be in use.)	
  1157                                  			   ; (Even if related hardware component
  1158                                  			   ;  does not exist!)
  1159 000007AD FB                      	sti
  1160                                  
  1161                                  	; top of stack = return address 
  1162                                  	; ('pminit_ok' for PMinit)
  1163                                  	
  1164 000007AE C3                      	retn
  1165                                  
  1166                                  pminit_ok:
  1167                                  	; 30/11/2020
  1168                                  	; Change VESA VBE3 BIOS text color in order to give
  1169                                  	; "VBE3 PMI initialization has been successed" meaning 	
  1170                                  
  1171 000007AF BE40810B00              	mov	esi, 0B8000h + 160*2 ; row 2
  1172 000007B4 89F7                    	mov	edi, esi
  1173                                  vbe3h_chcl:
  1174 000007B6 66AD                    	lodsw
  1175 000007B8 80FC0C                  	cmp	ah, 0Ch	; light red forecolor
  1176 000007BB 750D                    	jne	short display_mem_info
  1177 000007BD B40E                    	mov	ah, 0Eh ; yellow forecolor
  1178 000007BF 66AB                    	stosw
  1179 000007C1 EBF3                    	jmp	short vbe3h_chcl
  1180                                  
  1181                                  di0:
  1182                                  	; 30/11/2020
  1183                                  	; Memory allocation error !
  1184 000007C3 C605[CB080000]00        	mov	byte [vbe3], 0 ; disable VBE3
  1185                                  
  1186                                  display_mem_info:
  1187                                  	; 06/11/2014
  1188 000007CA E89C310000              	call	memory_info
  1189                                  	; 14/08/2015
  1190                                  	;call getch ; 28/02/2015
  1191                                  drv_init:
  1192 000007CF FB                      	sti	; Enable Interrupts 
  1193                                  	; 06/02/2015
  1194 000007D0 8B15[B0640000]          	mov	edx, [hd0_type] ; hd0, hd1, hd2, hd3
  1195 000007D6 668B1D[AE640000]        	mov	bx, [fd0_type] ; fd0, fd1
  1196                                  	; 22/02/2015
  1197 000007DD 6621DB                  	and	bx, bx
  1198 000007E0 7569                    	jnz	short di1
  1199                                  	;
  1200 000007E2 09D2                    	or 	edx, edx
  1201 000007E4 7577                    	jnz	short di2
  1202                                  	;
  1203                                  setup_error:
  1204 000007E6 BE[4A1F0100]            	mov 	esi, setup_error_msg
  1205                                  psem:	
  1206 000007EB AC                      	lodsb
  1207 000007EC 08C0                    	or	al, al
  1208                                  	;jz	short haltx ; 22/02/2015
  1209 000007EE 7474                    	jz	short di3
  1210 000007F0 56                      	push	esi
  1211                                  	; 13/05/2016
  1212 000007F1 BB07000000              	mov	ebx, 7	; Black background, 
  1213                                  			; light gray forecolor
  1214                                  			; Video page 0 (BH=0)
  1215 000007F6 E8DA180000              	call	_write_tty
  1216 000007FB 5E                      	pop	esi
  1217 000007FC EBED                    	jmp	short psem
  1218                                  
  1219                                  check_boch_plex86_vbe:
  1220                                  	; 20/11/2020
  1221                                  	; check Bochs/Plex86 VGABios VBE extension
  1222                                  	; (check if TRDOS 386 v2 is running on emulators)
  1223                                  	; BOCHS/QEMU/VIRTUALBOX
  1224                                  	;
  1225                                  	; ref: vbe_display_api.txt
  1226                                  
  1227                                  	; bochs/plex86 VGAbios VBE source code
  1228                                  	;  by Jeroen Janssen (2002)
  1229                                  	;  and Volker Ruppert (2003-2020)
  1230                                  
  1231 000007FE 29C0                    	sub	eax, eax ; 0
  1232 00000800 66BACE01                	mov	dx, 1CEh ; VBE_DISPI_IOPORT_INDEX
  1233 00000804 66EF                    	out	dx, ax ; VBE_DISPI_INDEX_ID register
  1234                                  	;mov	ax, 0B0C0h ; VBE_DISPI_ID0
  1235                                  	;mov	dx, 1CFh ; VBE_DISPI_IOPORT_DATA
  1236 00000806 6642                    	inc	dx
  1237                                  	;out	dx, ax
  1238                                  	;nop
  1239 00000808 66ED                    	in	ax, dx
  1240 0000080A 80FCB0                  	cmp	ah, 0B0h
  1241                                  	;jne	short not_boch_qemu_vbe
  1242 0000080D 75BB                    	jne	short display_mem_info
  1243 0000080F 3CC5                    	cmp	al, 0C5h ; it must be 0B0C4h or 0B0C5h ..
  1244                                  	;ja	short not_boch_qemu_vbe
  1245 00000811 77B7                    	ja	short display_mem_info
  1246 00000813 3CC0                    	cmp	al, 0C0h ; 0B0C0h to 0B0C5h .. ; Qemu
  1247                                  	;cmp	al, 0C4h ; 0BC04h or 0B0C5h is OK ; Bochs
  1248                                  	;jb	short not_boch_qemu_vbe
  1249 00000815 72B3                    	jb	short display_mem_info
  1250                                  
  1251                                  	; save VESA VBE2 bios (bochs/qemu) signature
  1252                                  	; for enabling VBE2 functions in TRDOS 386 v2 kernel
  1253 00000817 A2[CC080000]            	mov	[vbe2bios], al ; 0C4h or 0C5h (for BOCHS) 
  1254                                  			       ; (0C0h-0C5h for QEMU)
  1255 0000081C C605[2F5B0100]32        	mov	byte [vbe_vnumber], "2"
  1256                                  	; 26/11/2020
  1257                                  	; "BOCHS/QEMU/VIRTUALBOX VBE2 Video BIOS ..".
  1258 00000823 BE[115B0100]            	mov	esi, vbe2_bochs_vbios ; BOCH/QEMU vbios msg
  1259 00000828 B40E                    	mov	ah, 0Eh  ; Yellow font
  1260 0000082A E895310000              	call	print_kmsg
  1261                                  	
  1262                                  	; this is not necessary ! (20/11/2020)
  1263 0000082F 803D[CC080000]C4        	cmp	byte [vbe2bios], 0C4h 
  1264 00000836 7292                    	jb	short display_mem_info	; (QEMU) 
  1265                                  
  1266                                  	; Display kernel version message if 0E9h hack port
  1267                                  	; is enabled (bochs emulator feature)
  1268 00000838 66BAE900                	mov	dx, 0E9h ; hack port for BOCHS
  1269 0000083C BE[695B0100]            	mov	esi, kernel_version_msg
  1270                                  kvmsg_next_char:
  1271 00000841 AC                      	lodsb	
  1272 00000842 08C0                    	or	al, al
  1273 00000844 7502                    	jnz	short put_kvmsg_in_hack_port
  1274                                  not_boch_qemu_vbe:
  1275 00000846 EB82                     	jmp	short display_mem_info
  1276                                  put_kvmsg_in_hack_port:	
  1277 00000848 EE                      	out	dx, al
  1278 00000849 EBF6                    	jmp	short kvmsg_next_char
  1279                                  
  1280                                  di1:
  1281                                  	; supress 'jmp short T6'
  1282                                  	;  (activate fdc motor control code)
  1283 0000084B 66C705[2F090000]90-     	mov	word [T5], 9090h ; nop
  1283 00000853 90                 
  1284                                  	;
  1285                                  	;mov	ax, int_0Eh	; IRQ 6 handler
  1286                                  	;mov	di, 0Eh*4	; IRQ 6 vector
  1287                                  	;stosw
  1288                                  	;mov 	ax, cs
  1289                                  	;stosw
  1290                                  	;; 16/02/2015
  1291                                          ;;mov     dword [DISKETTE_INT], fdc_int ; IRQ 6 handler
  1292                                  	;
  1293 00000854 E8A4400000              	CALL	DSKETTE_SETUP	; Initialize Floppy Disks
  1294                                  	;
  1295 00000859 09D2                    	or	edx, edx
  1296 0000085B 7407                            jz      short di3
  1297                                  di2:
  1298 0000085D E8E2400000              	call   	DISK_SETUP	; Initialize Fixed Disks
  1299 00000862 7282                            jc      short setup_error
  1300                                  di3:
  1301 00000864 E8D6300000              	call	setup_rtc_int	; 22/05/2015 (dsectrpm.s)
  1302                                  	;
  1303 00000869 E872150100              	call	display_disks ; 07/03/2015  (Temporary)
  1304                                  di4: 
  1305                                  ;haltx:
  1306                                  	; 14/08/2015
  1307                                  	;call	getch ; 22/02/2015
  1308                                  	;sti	; Enable interrupts (for CPU)
  1309                                  ;	; 29/01/2016
  1310                                  ;	sub	ah, ah ;  read time count
  1311                                  ;	call	int1Ah
  1312                                  ;	mov	edx, ecx ; 18.2 * seconds
  1313                                  ;md_info_msg_wait1:
  1314                                  ;	; 29/01/2016
  1315                                  ;	mov	ah, 1
  1316                                  ;	call	int16h
  1317                                  ;	jz	short md_info_msg_wait2
  1318                                  ;	xor	ah, ah ; 0
  1319                                  ;       call    int16h
  1320                                  ;	jmp 	short md_info_msg_ok
  1321                                  ;md_info_msg_wait2:
  1322                                  ;	sub	ah, ah  ; read time count
  1323                                  ;	call	int1Ah
  1324                                  ;	cmp	edx, ecx ; ; 18.2 * seconds
  1325                                  ;	jna	short md_info_msg_wait3
  1326                                  ;	xchg 	edx, ecx	
  1327                                  ;md_info_msg_wait3:
  1328                                  ;	sub	ecx, edx
  1329                                  ;	cmp	ecx, 127 ; 7 seconds (18.2 * 7)
  1330                                  ;	jb	short md_info_msg_wait1		
  1331                                  ;md_info_msg_ok:
  1332                                  	; 08/09/2016
  1333 0000086E 0F20C0                  	mov	eax, cr0
  1334 00000871 A810                    	test	al, 10h  ; Bit 4, ET (Extension Type)
  1335 00000873 7408                    	jz	short sysinit
  1336                                  	; 27/02/2017
  1337 00000875 FE05[3C6B0100]          	inc	byte [fpready]
  1338                                  	; 80387 (FPU) is ready
  1339 0000087B DBE3                    	fninit ; Initialize Floating-Point Unit
  1340                                  sysinit:
  1341                                  	; 30/06/2015
  1342 0000087D E864620000              	call	sys_init
  1343                                  	;
  1344                                  	;jmp 	cpu_reset ; 22/02/2015
  1345                                  hang:  
  1346                                  	; 23/02/2015
  1347                                  	;sti			; Enable interrupts
  1348 00000882 F4                      	hlt
  1349                                  	;
  1350                                  	;nop
  1351                                  	;; 03/12/2014
  1352                                  	;; 28/08/2014
  1353                                  	;mov	ah, 11h
  1354                                  	;call	getc
  1355                                  	;jz      _c8
  1356                                  	;
  1357                                  	; 23/02/2015
  1358                                  	; 06/02/2015
  1359                                  	; 07/09/2014
  1360 00000883 31DB                    	xor	ebx, ebx
  1361 00000885 8A1D[AE5E0100]          	mov	bl, [ptty]	; active_page
  1362 0000088B 89DE                    	mov	esi, ebx
  1363 0000088D 66D1E6                  	shl 	si, 1
  1364 00000890 81C6[B05E0100]          	add	esi, ttychr
  1365 00000896 668B06                  	mov	ax, [esi]
  1366 00000899 6621C0                  	and	ax, ax
  1367                                  	;jz	short _c8
  1368 0000089C 74E4                    	jz	short hang
  1369 0000089E 66C7060000              	mov	word [esi], 0
  1370 000008A3 80FB03                  	cmp	bl, 3		; Video page 3
  1371                                  	;jb	short _c8
  1372 000008A6 72DA                    	jb	short hang
  1373                                  	;	
  1374                                  	; 13/05/2016
  1375                                  	; 07/09/2014
  1376                                  nxtl:
  1377 000008A8 6653                    	push	bx
  1378 000008AA 66BB0E00                	mov	bx, 0Eh 	; Yellow character 
  1379                                  				; on black background
  1380                                  				; bh = 0 (video page 0)
  1381                                  				; Retro UNIX 386 v1 - Video Mode 0
  1382                                  				; (PC/AT Video Mode 3 - 80x25 Alpha.)
  1383 000008AE 6650                    	push	ax
  1384 000008B0 E820180000              	call 	_write_tty
  1385 000008B5 6658                    	pop	ax
  1386 000008B7 665B                    	pop	bx
  1387 000008B9 3C0D                    	cmp	al, 0Dh		; carriage return (enter)
  1388                                  	;jne	short _c8
  1389 000008BB 75C5                    	jne	short hang
  1390 000008BD B00A                    	mov	al, 0Ah		; next line
  1391 000008BF EBE7                    	jmp	short nxtl
  1392                                  	
  1393                                  ;_c8:
  1394                                  ;	; 25/08/2014
  1395                                  ;	cli				; Disable interrupts
  1396                                  ;	mov	al, [scounter + 1]
  1397                                  ;	and	al, al
  1398                                  ;	jnz	hang
  1399                                  ;	call	rtc_p
  1400                                  ;	jmp     hang
  1401                                  
  1402                                  	; 27/08/2014
  1403                                  	; 20/08/2014
  1404                                  printk:
  1405                                          ;mov    edi, [scr_row]
  1406                                  pkl:
  1407 000008C1 AC                      	lodsb
  1408 000008C2 08C0                    	or 	al, al
  1409 000008C4 7404                    	jz	short pkr
  1410 000008C6 66AB                    	stosw
  1411 000008C8 EBF7                    	jmp	short pkl
  1412                                  pkr:
  1413 000008CA C3                      	retn
  1414                                  
  1415                                  ; 14/11/2020 (TRDOS 386 v2.0.3)
  1416 000008CB 00                      vbe3:	db 0  ; VESA VBE version (must be 03h)
  1417                                  	      ; for using video bios calls in protected mode
  1418                                  vbe2bios:
  1419 000008CC B0                      	db 0B0h ; 
  1420                                  pmid_addr: 		
  1421 000008CD 0000                    	dw 0  ; > 0 if 'PMID' sign is found 
  1422                                  	      ;	('pmid' offset addr in VGA bios seg, 0C000h)	 		
  1423                                  		
  1424                                  ; 28/02/2017
  1425                                  ; 22/01/2017
  1426                                  ; 15/01/2017
  1427                                  ; 14/01/2017
  1428                                  ; 02/01/2017
  1429                                  ; 25/12/2016
  1430                                  ; 19/12/2016
  1431                                  ; 10/12/2016 (callback)
  1432                                  ; 06/06/2016
  1433                                  ; 23/05/2016
  1434                                  ; 22/05/2016 - TRDOS 386 (TRDOS v2.0) Timer Event Modifications
  1435                                  ; 25/07/2015
  1436                                  ; 14/05/2015 (multi tasking -time sharing- 'clock', x_timer)
  1437                                  ; 17/02/2015
  1438                                  ; 06/02/2015 (unix386.s)
  1439                                  ; 11/12/2014 - 22/12/2014 (dsectrm2.s) 
  1440                                  ;
  1441                                  ; IBM PC-XT Model 286 Source Code - BIOS2.ASM (06/10/85)
  1442                                  ;
  1443                                  ;-- HARDWARE INT  08 H - ( IRQ LEVEL 0 ) ---------------------------------------
  1444                                  ;	THIS ROUTINE HANDLES THE TIMER INTERRUPT FROM FROM CHANNEL 0 OF        :
  1445                                  ;	THE 8254 TIMER.  INPUT FREQUENCY IS 1.19318 MHZ AND THE DIVISOR        :
  1446                                  ;	IS 65536, RESULTING IN APPROXIMATELY 18.2 INTERRUPTS EVERY SECOND.     :
  1447                                  ;									       :
  1448                                  ;	THE INTERRUPT HANDLER MAINTAINS A COUNT (40:6C) OF INTERRUPTS SINCE    :
  1449                                  ;	POWER ON TIME, WHICH MAY BE USED TO ESTABLISH TIME OF DAY.	       :
  1450                                  ;	THE INTERRUPT HANDLER ALSO DECREMENTS THE MOTOR CONTROL COUNT (40:40)  :
  1451                                  ;	OF THE DISKETTE, AND WHEN IT EXPIRES, WILL TURN OFF THE 	       :
  1452                                  ;	DISKETTE MOTOR(s), AND RESET THE MOTOR RUNNING FLAGS.		       :
  1453                                  ;	THE INTERRUPT HANDLER WILL ALSO INVOKE A USER ROUTINE THROUGH	       :
  1454                                  ;	INTERRUPT 1CH AT EVERY TIME TICK.  THE USER MUST CODE A 	       :
  1455                                  ;	ROUTINE AND PLACE THE CORRECT ADDRESS IN THE VECTOR TABLE.	       :
  1456                                  ;-------------------------------------------------------------------------------
  1457                                  ;
  1458                                  
  1459                                  timer_int:	; IRQ 0
  1460                                  ;int_08h:	; Timer
  1461                                  	; 14/10/2015
  1462                                  	; Here, we are simulating system call entry (for task switch)
  1463                                  	; (If multitasking is enabled, 
  1464                                  	; 'clock' procedure may jump to 'sysrelease')
  1465                                  
  1466 000008CF 1E                      	push	ds
  1467 000008D0 06                      	push	es
  1468 000008D1 0FA0                    	push	fs
  1469 000008D3 0FA8                    	push	gs
  1470                                  
  1471 000008D5 60                      	pushad	; eax, ecx, edx, ebx, esp -before pushad-, ebp, esi, edi
  1472 000008D6 66B91000                	mov     cx, KDATA
  1473 000008DA 8ED9                            mov     ds, cx
  1474 000008DC 8EC1                            mov     es, cx
  1475 000008DE 8EE1                            mov     fs, cx
  1476 000008E0 8EE9                            mov     gs, cx
  1477                                  
  1478 000008E2 0F20D9                  	mov	ecx, cr3
  1479 000008E5 890D[5C040300]          	mov	[cr3reg], ecx ; save current cr3 register value/content
  1480                                  
  1481                                  	; 14/01/2017
  1482 000008EB 3B0D[805E0100]          	cmp 	ecx, [k_page_dir]
  1483 000008F1 7409                    	je	short T3
  1484                                  
  1485 000008F3 8B0D[805E0100]          	mov	ecx, [k_page_dir]
  1486 000008F9 0F22D9                  	mov	cr3, ecx
  1487                                  T3:
  1488                                  	;sti				; INTERRUPTS BACK ON
  1489 000008FC 66FF05[005F0100]        	INC	word [TIMER_LOW]	; INCREMENT TIME
  1490 00000903 7507                    	JNZ	short T4		; GO TO TEST_DAY
  1491 00000905 66FF05[025F0100]        	INC	word [TIMER_HIGH]	; INCREMENT HIGH WORD OF TIME
  1492                                  T4:					; TEST_DAY
  1493 0000090C 66833D[025F0100]18      	CMP	word [TIMER_HIGH],018H	; TEST FOR COUNT EQUALING 24 HOURS
  1494 00000914 7519                    	JNZ	short T5		; GO TO DISKETTE_CTL
  1495 00000916 66813D[005F0100]B0-     	CMP	word [TIMER_LOW],0B0H
  1495 0000091E 00                 
  1496 0000091F 750E                    	JNZ	short T5		; GO TO DISKETTE_CTL
  1497                                  
  1498                                  ;-----	TIMER HAS GONE 24 HOURS
  1499                                  	;;SUB	AX,AX
  1500                                  	;MOV	[TIMER_HIGH],AX
  1501                                  	;MOV	[TIMER_LOW],AX
  1502 00000921 29C0                    	sub	eax, eax
  1503 00000923 A3[005F0100]            	mov	[TIMER_LH], eax
  1504                                  	;	
  1505 00000928 C605[045F0100]01        	MOV	byte [TIMER_OFL],1
  1506                                  
  1507                                  ;-----	TEST FOR DISKETTE TIME OUT
  1508                                  
  1509                                  T5:
  1510                                  	; 23/12/2014
  1511 0000092F EB1D                    	jmp	short T6		; will be replaced with nop, nop
  1512                                  					; (9090h) if a floppy disk
  1513                                  					; is detected.
  1514                                  	;mov	al,[CS:MOTOR_COUNT]
  1515 00000931 A0[075F0100]            	mov	al, [MOTOR_COUNT]
  1516 00000936 FEC8                    	dec	al
  1517                                  	;mov	[CS:MOTOR_COUNT], al	; DECREMENT DISKETTE MOTOR CONTROL
  1518 00000938 A2[075F0100]            	mov	[MOTOR_COUNT], al
  1519                                  	;mov	[ORG_MOTOR_COUNT], al
  1520 0000093D 750F                    	JNZ	short T6		; RETURN IF COUNT NOT OUT
  1521 0000093F B0F0                    	mov 	al,0F0h
  1522                                  	;AND	[CS:MOTOR_STATUS],al 	; TURN OFF MOTOR RUNNING BITS
  1523 00000941 2005[065F0100]          	and	[MOTOR_STATUS], al
  1524                                  	;and	[ORG_MOTOR_STATUS], al
  1525 00000947 B00C                    	MOV	AL,0CH			; bit 3 = enable IRQ & DMA, 
  1526                                  					; bit 2 = enable controller
  1527                                  					;	1 = normal operation
  1528                                  					;	0 = reset	
  1529                                  					; bit 0, 1 = drive select
  1530                                  					; bit 4-7 = motor running bits 
  1531 00000949 66BAF203                	MOV	DX,03F2H		; FDC CTL PORT
  1532 0000094D EE                      	OUT	DX,AL			; TURN OFF THE MOTOR
  1533                                  T6:	
  1534                                  	;inc	word [CS:wait_count]	; 22/12/2014 (byte -> word)
  1535                                  					; TIMER TICK INTERRUPT
  1536                                  	;;inc	word [wait_count] ;;27/02/2015
  1537                                  	;INT	1CH			; TRANSFER CONTROL TO A USER ROUTINE
  1538                                  	;cli
  1539 0000094E E857040000              	call 	u_timer			; TRANSFER CONTROL TO A USER ROUTINE
  1540                                  	; 23/05/2016
  1541 00000953 E8C8F50000              	call	clock			; Multi Tasking control procedure
  1542                                  T7:
  1543                                  	; 14/10/2015
  1544 00000958 B020                    	MOV	AL,EOI			; GET END OF INTERRUPT MASK
  1545 0000095A FA                      	CLI				; DISABLE INTERRUPTS TILL STACK CLEARED
  1546 0000095B E620                    	OUT	INTA00,AL		; END OF INTERRUPT TO 8259 - 1	
  1547                                  	;
  1548                                  rtc_int_2:
  1549                                  	; 26/12/2016
  1550                                  	;mov	ecx, [cr3reg]
  1551                                  	; 13/01/2017
  1552 0000095D 803D[D4030300]00        	cmp	byte [u.t_lock], 0  	; T_LOCK
  1553 00000964 7730                    	ja	short timer_int_return  ; Timer Lock : 'sysrele' is needed !
  1554                                  	; 28/02/2017
  1555                                  	; We need to exit if the user's IRQ callback service is in progress!
  1556                                  	; (To prevent a conflict!)
  1557 00000966 803D[D8030300]00        	cmp	byte [u.r_lock], 0	; R_LOCK, IRQ callback service lock !
  1558 0000096D 7727                    	ja	short timer_int_return  ; Timer Lock : 'sysrele' is needed !	
  1559                                  	; 15/01/2017
  1560 0000096F 803D[106B0100]02        	cmp	byte [priority], 2
  1561 00000976 733A                    	jnb	short T8  ; current process has a timer event (15/01/2017)
  1562                                  	; 22/05/2016
  1563 00000978 803D[116B0100]00        	cmp	byte [p_change], 0 ; in 'set_run_sequence', in 'rtc_p'
  1564 0000097F 7615                    	jna	short timer_int_return ; 23/05/2016
  1565                                  
  1566                                  	; 15/01/2017
  1567                                  	
  1568                                  	; present process must be changed with high priority process	
  1569                                  	;xor	al, al
  1570 00000981 31C0                    	xor	eax, eax ; 26/12/2016
  1571 00000983 A2[116B0100]            	mov	[p_change], al ; 0
  1572                                  	;mov	byte [priority], 2 ; 15/01/2017 (there is a timer event)
  1573                                  
  1574 00000988 803D[5B030300]FF        	cmp     byte [sysflg], 0FFh ; user or system space ?
  1575 0000098F 7416                    	je	short rtc_int_3     ; user space ([sysflg]= 0FFh)
  1576                                  
  1577                                  	; system space, wait for 'sysret'
  1578                                  	; to change running process 	
  1579                                  	; with high priority (event) process
  1580                                  
  1581 00000991 A2[A8030300]            	mov	[u.quant], al ; 0
  1582                                  
  1583                                  timer_int_return: ; 23/05/2016 - jump from 'rtc_int' ('rtc_int_2')
  1584 00000996 8B0D[5C040300]          	mov 	ecx, [cr3reg] 	; previous value/content of cr3 register
  1585 0000099C 0F22D9                   	mov	cr3, ecx	; restore cr3 register content
  1586                                  	;
  1587 0000099F 61                      	popad ; edi, esi, ebp, temp (icrement esp by 4), ebx, edx, ecx, eax
  1588                                  	;
  1589 000009A0 0FA9                    	pop	gs
  1590 000009A2 0FA1                    	pop	fs
  1591 000009A4 07                      	pop	es
  1592 000009A5 1F                      	pop	ds
  1593                                  	;
  1594 000009A6 CF                      	iretd	; return from interrupt
  1595                                  
  1596                                  rtc_int_3:
  1597 000009A7 FE05[5B030300]          	inc	byte [sysflg] 	; now, we are in system space
  1598                                  	;
  1599 000009AD E908C60000                      jmp     sysrelease ; change running process immediatelly 
  1600                                  
  1601                                  T8:
  1602                                  	; 13/01/2017 (eax -> ebx)
  1603                                  	; callback checking... (19/12/2016)
  1604 000009B2 31DB                    	xor	ebx, ebx
  1605 000009B4 871D[D0030300]          	xchg	ebx, [u.tcb] ; callback address (0 = normal return)
  1606 000009BA 09DB                    	or	ebx, ebx
  1607 000009BC 74D8                    	jz	short timer_int_return
  1608                                  
  1609                                  	; Set user's callback routine as return address from this interrupt
  1610                                  	; and set normal return address as return address from callback
  1611                                  	; routine!!! (19/12/2016)
  1612                                  	
  1613                                  	; 14/01/2017
  1614                                  	; 13/01/2017 - Timer Lock (T_LOCK)
  1615 000009BE FE05[D4030300]          	inc	byte [u.t_lock]
  1616 000009C4 8A0D[5B030300]          	mov	cl, [sysflg]
  1617 000009CA 880D[D5030300]          	mov	[u.t_mode], cl 
  1618                                  
  1619 000009D0 8B2D[1C5E0100]          	mov	ebp, [tss.esp0] ; kernel stack address (for ring 0)
  1620 000009D6 83ED14                  	sub	ebp, 20		; eip, cs, eflags, esp, ss
  1621 000009D9 892D[5C030300]           	mov	[u.sp], ebp
  1622 000009DF 8925[60030300]          	mov	[u.usp], esp
  1623                                  
  1624                                  	;or	word [ebp+8], 200h ; 22/01/2017, force enabling interrupts
  1625                                  
  1626 000009E5 8B44241C                	mov	eax, [esp+28] ; pushed eax
  1627 000009E9 A3[64030300]            	mov	[u.r0], eax
  1628                                  
  1629 000009EE E823E20000              	call	wswap ; save user's registers & status
  1630                                  
  1631                                  	; software int is in ring 0 but timer int must return to ring 3
  1632                                  	; so, ring 3 return address and stack registers
  1633                                  	; (eip, cs, eflags, esp, ss) 
  1634                                  	; must be copied to timer int return
  1635                                  	; eip will be replaced by callback service routine address
  1636                                  
  1637 000009F3 C605[5B030300]FF        	mov	byte [sysflg], 0FFh ; user mode
  1638                                  
  1639                                  	; system mode (system call)
  1640                                  	;mov	ebp, [u.sp] ; EIP (u), CS (UCODE), EFLAGS (u),
  1641                                  			    ; ESP (u), SS (UDATA)
  1642                                  
  1643 000009FA 8B4510                  	mov	eax, [ebp+16]	; SS (UDATA
  1644 000009FD 89E6                    	mov	esi, esp
  1645 000009FF 50                      	push	eax
  1646 00000A00 50                      	push	eax
  1647 00000A01 89E7                    	mov	edi, esp
  1648 00000A03 893D[60030300]          	mov	[u.usp], edi
  1649 00000A09 B908000000              	mov	ecx, ((ESPACE/4) - 4) ; except DS, ES, FS, GS
  1650 00000A0E F3A5                    	rep	movsd
  1651 00000A10 B104                    	mov	cl, 4	
  1652 00000A12 F3AB                    	rep	stosd
  1653 00000A14 893D[5C030300]          	mov	[u.sp], edi
  1654 00000A1A 89EE                    	mov	esi, ebp
  1655 00000A1C B105                    	mov	cl, 5 ; EIP (u), CS (UCODE), EFLAGS (u), ESP (u), SS (UDATA)
  1656 00000A1E F3A5                    	rep	movsd
  1657                                  
  1658 00000A20 8B0D[B8030300]          	mov	ecx, [u.pgdir]
  1659 00000A26 890D[5C040300]          	mov	[cr3reg], ecx
  1660                                  
  1661                                  	; 13/01/207 (eax -> ebx)
  1662                                  	; EBX = callback routine address (virtual, not physical address!)
  1663                                  
  1664                                  	; 09/01/2017
  1665                                  	; !!! CALLBACK ROUTINE MUST BE ENDED/RETURNED WITH 'sysrele'
  1666                                  	;     system call !!!	
  1667                                  	; 25/12/2016
  1668                                  	; Callback Note: (19/12/2016)
  1669                                  	; !!! CALLBACK ROUTINE MUST BE ENDED/RETURNED WITH 'RETN' !!!
  1670                                  	;	pushf ; save flags	
  1671                                  	; 	<callback service code>
  1672                                  	; 	popf  ; restore flags
  1673                                  	; 	retn ; return to normal running address
  1674                                  	;
  1675                                  
  1676                                  	; 15/01/2017
  1677                                  	; 14/01/2017
  1678                                  	; 13/01/2017 (eax -> ebx)
  1679                                  	; 10/01/2017
  1680                                  set_callback_addr:
  1681                                  	; 09/01/2017 (**)
  1682                                  	; 02/01/2017 (*)
  1683                                  	; 25/12/2016 (*)
  1684                                  	; 19/12/2016 (TRDOS 386 feature only!)
  1685                                  	;
  1686                                  	; This routine sets return address
  1687                                  	; to start of user's interrupt
  1688                                  	; service (callback) address
  1689                                  	;; and sets callback 'retn' address to normal
  1690                                  	;; return address of user's running code! 
  1691                                  	;
  1692                                  	; INPUT:
  1693                                  	;	EBX = callback routine/service address
  1694                                  	;	      (virtual, not physical address!)	
  1695                                  	;	[u.sp] = kernel stack, points to
  1696                                  	;		 user's EIP,CS,EFLAGS,ESP,SS
  1697                                  	;		 registers.
  1698                                  	; OUTPUT:
  1699                                  	;	EIP (user) = callback (service) address
  1700                                  	;	CS (user) = UCODE
  1701                                  	;	EFLAGS (user) = flags before callback 	 
  1702                                  	;       ESP (user) = ESP-4 (user, before callback) 
  1703                                  	;	[ESP](user) = EIP (user) before callback
  1704                                  	;
  1705                                  	; Note: If CPU was in user mode while entering 
  1706                                  	;	the timer interrupt service routine,
  1707                                  	;	'IRET' will get return to callback routine
  1708                                  	;	immediately. If CPU was in system/kernel mode  
  1709                                  	;	'iret' will get return to system call and
  1710                                  	;	then, callback routine will be return address
  1711                                  	;	from system call. (User's callback/service code
  1712                                  	;	will be able to return to normal return address
  1713                                  	;	via an 'retn' at the end.) 
  1714                                  	;
  1715                                  	; Note(**): User's callback service code must be ended
  1716                                  	;	with a 'sysrele' sytstem call ! (09/01/2017)
  1717                                  	;
  1718                                  	;	For example:
  1719                                  	;
  1720                                  	;	timer_callback:
  1721                                  	;	    ...	 
  1722                                    	;	    inc	dword [time_counter]
  1723                                  	;	    ...
  1724                                  	;	    mov eax, 39 ; 'sysrele'
  1725                                  	;	    int 40h ; TRDOS 386 system call (interrupt)		
  1726                                  	;
  1727                                  	;
  1728                                  	;; Note(*): User's callback service code must preserve cpu 
  1729                                  	;;	flags if it has any instructions which changes
  1730                                  	;;	flags in the service code. (25/12/2016)
  1731                                  	;;
  1732                                  	;;	For example:
  1733                                  	;;
  1734                                  	;;	timer_callback:
  1735                                  	;;	    pushf ; save flags
  1736                                  	;;	    ; this instruction changes zero flag
  1737                                    	;;	    inc	dword [time_counter]
  1738                                  	;;	    popf ; restore flags
  1739                                  	;;	    retn ; return to normal user code
  1740                                  	;;		  (which is interrupted by the 
  1741                                  	;;		   timer interput) 	
  1742                                  	;;
  1743                                  
  1744                                  	; 15/01/2017
  1745 00000A2C 8B2D[5C030300]          	mov	ebp, [u.sp]; kernel's stack, points to EIP (user)
  1746 00000A32 895D00                  	mov	[ebp], ebx
  1747 00000A35 E95CFFFFFF              	jmp	timer_int_return
  1748                                  
  1749                                  	; 15/01/2017
  1750                                  	; 13/01/2017
  1751                                  	; 19/12/2016
  1752                                  	; 06/06/2016
  1753                                  	; 23/05/2016
  1754                                  	; 22/05/2016
  1755                                  	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
  1756                                  	; 26/02/2015
  1757                                  	; 07/09/2014
  1758                                  	; 25/08/2014
  1759                                  rtc_int:       ; Real Time Clock Interrupt (IRQ 8)
  1760                                  	; 22/05/2016
  1761 00000A3A 1E                      	push	ds ; ** ; 23/05/2016
  1762 00000A3B 50                      	push	eax ; *
  1763 00000A3C 66B81000                	mov	ax, KDATA
  1764 00000A40 8ED8                    	mov	ds, ax
  1765                                  	;
  1766 00000A42 8A25[FE5E0100]          	mov	ah, [RTC_2Hz] ;  2 Hz interrupt to 1 Hz function
  1767 00000A48 80F401                  	xor	ah, 1
  1768 00000A4B 8825[FE5E0100]          	mov	[RTC_2Hz], ah ; 1 = 0.5 second, 0 = 1 second
  1769 00000A51 753B                    	jnz	short rtc_int_return ; half second
  1770                                  	; 1 second
  1771                                  rtc_int_0:
  1772                                  	; 22/05/2016
  1773 00000A53 58                      	pop	eax ; *
  1774                                  	;
  1775                                  	; 14/10/2015 ('timer_int')
  1776                                  	; Here, we are simulating system call entry (for task switch)
  1777                                  	; (If multitasking is enabled, 
  1778                                  	; 'clock' procedure may jump to 'sysrelease')
  1779                                  	;push	ds ; ** ; 23/05/2016
  1780 00000A54 06                      	push	es
  1781 00000A55 0FA0                    	push	fs
  1782 00000A57 0FA8                    	push	gs
  1783 00000A59 60                      	pushad  ; eax, ecx, edx, ebx, esp -before pushad-, ebp, esi, edi
  1784 00000A5A 66B91000                	mov     cx, KDATA
  1785                                          ;mov    ds, cx ; 06/06/2016
  1786 00000A5E 8EC1                            mov     es, cx
  1787 00000A60 8EE1                            mov     fs, cx
  1788 00000A62 8EE9                            mov     gs, cx
  1789                                  	;
  1790 00000A64 0F20D9                  	mov	ecx, cr3
  1791 00000A67 890D[5C040300]          	mov	[cr3reg], ecx ; save current cr3 register value/content
  1792                                  	;
  1793 00000A6D 803D[D4030300]00        	cmp	byte [u.t_lock], 0 ; timer lock (callback) status ?
  1794 00000A74 7711                    	ja	short rtc_int_1	   ; yes
  1795                                  
  1796                                  	; 15/01/2017
  1797 00000A76 3B0D[805E0100]          	cmp 	ecx, [k_page_dir]
  1798 00000A7C 7409                    	je	short rtc_int_1
  1799                                  
  1800 00000A7E 8B0D[805E0100]          	mov	ecx, [k_page_dir]
  1801 00000A84 0F22D9                  	mov	cr3, ecx
  1802                                  rtc_int_1:
  1803                                  	; Timer event (kernel) functions must be performed with
  1804                                  	; 1 second intervals - TRDOS 386 (TRDOS v2.0) feature ! -
  1805                                   	;	
  1806                                  	; 25/08/2014
  1807 00000A87 E81A030000              	call	rtc_p  ; 19/05/2016 - major modification 
  1808                                  	
  1809                                  	; 23/05/2016
  1810 00000A8C 28E4                    	sub	ah, ah ; 0
  1811                                  	; 22/05/2016 - TRDOS 386 timer event modifications
  1812                                  rtc_int_return: ; 19/05/2016
  1813                                  	; 22/02/2015 - dsectpm.s
  1814                                  	; [ source: http://wiki.osdev.org/RTC ]
  1815                                  	; read status register C to complete procedure
  1816                                  	;(it is needed to get a next IRQ 8) 
  1817 00000A8E B00C                    	mov	al, 0Ch ; 
  1818 00000A90 E670                    	out	70h, al ; select register C
  1819 00000A92 90                      	nop
  1820 00000A93 E471                    	in	al, 71h ; just throw away contents
  1821                                  	; 22/02/2015
  1822 00000A95 B020                    	MOV	AL,EOI		; END OF INTERRUPT
  1823                                  	;CLI			; DISABLE INTERRUPTS TILL STACK CLEARED
  1824 00000A97 E6A0                    	OUT	INTB00,AL	; FOR CONTROLLER #2
  1825                                  
  1826                                  	; 23/05/2016
  1827 00000A99 B020                    	MOV	AL,EOI		; GET END OF INTERRUPT MASK
  1828 00000A9B FA                      	CLI			; DISABLE INTERRUPTS TILL STACK CLEARED
  1829 00000A9C E620                    	OUT	INTA00,AL	; END OF INTERRUPT TO 8259 - 1	
  1830                                  	;
  1831                                  	; 23/05/2016
  1832 00000A9E 20E4                    	and	ah, ah
  1833 00000AA0 0F84B7FEFFFF                    jz      rtc_int_2
  1834                                  	
  1835                                  	; ah = 1 (half second)
  1836 00000AA6 58                      	pop	eax ; *
  1837 00000AA7 1F                      	pop	ds  ; **
  1838 00000AA8 CF                      	iretd
  1839                                  
  1840                                  ; ////////////////
  1841                                  
  1842                                  	; 28/08/2014
  1843                                  irq0:
  1844 00000AA9 6A00                            push 	dword 0
  1845 00000AAB EB48                    	jmp	short which_irq
  1846                                  irq1:
  1847 00000AAD 6A01                            push 	dword 1
  1848 00000AAF EB44                    	jmp	short which_irq
  1849                                  irq2:
  1850 00000AB1 6A02                            push 	dword 2
  1851 00000AB3 EB40                    	jmp	short which_irq
  1852                                  irq3:
  1853                                  	; 20/11/2015
  1854                                  	; 24/10/2015
  1855 00000AB5 2EFF15[DE010100]        	call	dword [cs:com2_irq3]
  1856 00000ABC 6A03                    	push 	dword 3
  1857 00000ABE EB35                    	jmp	short which_irq
  1858                                  irq4:
  1859                                  	; 20/11/2015
  1860                                  	; 24/10/2015
  1861 00000AC0 2EFF15[DA010100]        	call	dword [cs:com1_irq4]
  1862 00000AC7 6A04                            push 	dword 4
  1863 00000AC9 EB2A                    	jmp	short which_irq
  1864                                  irq5:
  1865 00000ACB 6A05                            push 	dword 5
  1866 00000ACD EB26                    	jmp	short which_irq
  1867                                  irq6:
  1868 00000ACF 6A06                            push 	dword 6
  1869 00000AD1 EB22                    	jmp	short which_irq
  1870                                  irq7:
  1871 00000AD3 6A07                            push 	dword 7
  1872 00000AD5 EB1E                    	jmp	short which_irq
  1873                                  irq8:
  1874 00000AD7 6A08                            push 	dword 8
  1875 00000AD9 EB1A                    	jmp	short which_irq
  1876                                  irq9:
  1877 00000ADB 6A09                            push 	dword 9
  1878 00000ADD EB16                    	jmp	short which_irq
  1879                                  irq10:
  1880 00000ADF 6A0A                            push 	dword 10
  1881 00000AE1 EB12                    	jmp	short which_irq
  1882                                  irq11:
  1883 00000AE3 6A0B                            push 	dword 11
  1884 00000AE5 EB0E                    	jmp	short which_irq
  1885                                  irq12:
  1886 00000AE7 6A0C                            push 	dword 12
  1887 00000AE9 EB0A                    	jmp	short which_irq
  1888                                  irq13:
  1889 00000AEB 6A0D                            push 	dword 13
  1890 00000AED EB06                    	jmp	short which_irq
  1891                                  irq14:
  1892 00000AEF 6A0E                            push 	dword 14
  1893 00000AF1 EB02                    	jmp	short which_irq
  1894                                  irq15:
  1895 00000AF3 6A0F                            push 	dword 15
  1896                                  	;jmp	short which_irq
  1897                                  
  1898                                  	; 22/01/2017
  1899                                  	; 19/10/2015
  1900                                  	; 29/08/2014
  1901                                  	; 21/08/2014
  1902                                  which_irq:
  1903 00000AF5 870424                  	xchg	eax, [esp]  ; 28/08/2014
  1904 00000AF8 53                      	push	ebx
  1905 00000AF9 56                      	push	esi
  1906 00000AFA 57                      	push	edi
  1907 00000AFB 1E                      	push 	ds
  1908 00000AFC 06                      	push 	es
  1909                                  	;
  1910 00000AFD 88C3                    	mov	bl, al
  1911                                  	;
  1912 00000AFF B810000000              	mov	eax, KDATA
  1913 00000B04 8ED8                    	mov	ds, ax
  1914 00000B06 8EC0                    	mov	es, ax
  1915                                  	; 19/10/2015
  1916 00000B08 FC                      	cld
  1917                                          ; 27/08/2014
  1918 00000B09 8105[3C1C0100]A000-             add     dword [scr_row], 0A0h
  1918 00000B11 0000               
  1919                                  	;
  1920 00000B13 B417                    	mov	ah, 17h	; blue (1) background, 
  1921                                  			; light gray (7) forecolor
  1922 00000B15 8B3D[3C1C0100]                  mov     edi, [scr_row]
  1923 00000B1B B049                    	mov	al, 'I'
  1924 00000B1D 66AB                    	stosw
  1925 00000B1F B052                    	mov	al, 'R'
  1926 00000B21 66AB                    	stosw
  1927 00000B23 B051                    	mov	al, 'Q'
  1928 00000B25 66AB                    	stosw
  1929 00000B27 B020                    	mov	al, ' '
  1930 00000B29 66AB                    	stosw
  1931 00000B2B 88D8                    	mov	al, bl
  1932 00000B2D 3C0A                    	cmp	al, 10
  1933 00000B2F 7208                    	jb	short ii1
  1934 00000B31 B031                    	mov	al, '1'
  1935 00000B33 66AB                    	stosw
  1936 00000B35 88D8                    	mov	al, bl
  1937 00000B37 2C0A                    	sub	al, 10
  1938                                  ii1:
  1939 00000B39 0430                    	add	al, '0'
  1940 00000B3B 66AB                    	stosw
  1941 00000B3D B020                    	mov	al, ' '
  1942 00000B3F 66AB                    	stosw
  1943 00000B41 B021                    	mov	al, '!'
  1944 00000B43 66AB                    	stosw
  1945 00000B45 B020                    	mov	al, ' '
  1946 00000B47 66AB                    	stosw
  1947                                  	; 23/02/2015
  1948 00000B49 80FB07                  	cmp	bl, 7 ; check for IRQ 8 to IRQ 15 
  1949 00000B4C 7604                    	jna	ii2
  1950                                  	; 22/01/2017
  1951 00000B4E B020                    	mov	al, 20h  ; END OF INTERRUPT COMMAND TO
  1952 00000B50 E6A0                    	out	0A0h, al ; the 2nd 8259
  1953                                  ii2:
  1954 00000B52 B020                    	mov	al, 20h  ; END OF INTERRUPT COMMAND TO
  1955 00000B54 E620                    	out	20h, al ; the 2nd 8259
  1956 00000B56 E9CD010000              	jmp     iiret
  1957                                  	;
  1958                                  	; 22/08/2014
  1959                                  	;mov	al, 20h ; END OF INTERRUPT COMMAND TO 8259
  1960                                  	;out	20h, al	; 8259 PORT
  1961                                  	;
  1962                                  	;pop	es
  1963                                  	;pop	ds
  1964                                  	;pop	edi
  1965                                  	;pop	esi
  1966                                  	;pop	ebx
  1967                                  	;pop 	eax
  1968                                  	;iret
  1969                                  
  1970                                  	; 02/04/2015
  1971                                  	; 25/08/2014
  1972                                  exc0:
  1973 00000B5B 6A00                            push 	dword 0
  1974 00000B5D E990000000                      jmp     cpu_except
  1975                                  exc1:
  1976 00000B62 6A01                            push 	dword 1
  1977 00000B64 E989000000                      jmp     cpu_except
  1978                                  exc2:
  1979 00000B69 6A02                            push 	dword 2
  1980 00000B6B E982000000                      jmp     cpu_except
  1981                                  exc3:
  1982 00000B70 6A03                            push 	dword 3
  1983 00000B72 EB7E                            jmp     cpu_except
  1984                                  exc4:
  1985 00000B74 6A04                            push 	dword 4
  1986 00000B76 EB7A                            jmp     cpu_except
  1987                                  exc5:
  1988 00000B78 6A05                            push 	dword 5
  1989 00000B7A EB76                            jmp     cpu_except
  1990                                  exc6:
  1991 00000B7C 6A06                            push 	dword 6
  1992 00000B7E EB72                            jmp     cpu_except
  1993                                  exc7:
  1994 00000B80 6A07                            push 	dword 7
  1995 00000B82 EB6E                            jmp     cpu_except
  1996                                  exc8:
  1997                                  	; [esp] = Error code
  1998 00000B84 6A08                            push 	dword 8
  1999 00000B86 EB5C                            jmp     cpu_except_en
  2000                                  exc9:
  2001 00000B88 6A09                            push 	dword 9
  2002 00000B8A EB66                            jmp     cpu_except
  2003                                  exc10:
  2004                                  	; [esp] = Error code
  2005 00000B8C 6A0A                            push 	dword 10
  2006 00000B8E EB54                            jmp     cpu_except_en
  2007                                  exc11:
  2008                                  	; [esp] = Error code
  2009 00000B90 6A0B                            push 	dword 11
  2010 00000B92 EB50                            jmp     cpu_except_en
  2011                                  exc12:
  2012                                  	; [esp] = Error code
  2013 00000B94 6A0C                            push 	dword 12
  2014 00000B96 EB4C                            jmp     cpu_except_en
  2015                                  exc13:
  2016                                  	; [esp] = Error code
  2017 00000B98 6A0D                            push 	dword 13
  2018 00000B9A EB48                            jmp     cpu_except_en
  2019                                  exc14:
  2020                                  	; [esp] = Error code
  2021 00000B9C 6A0E                            push 	dword 14
  2022 00000B9E EB44                    	jmp	short cpu_except_en
  2023                                  exc15:
  2024 00000BA0 6A0F                            push 	dword 15
  2025 00000BA2 EB4E                            jmp     cpu_except
  2026                                  exc16:
  2027 00000BA4 6A10                            push 	dword 16
  2028 00000BA6 EB4A                            jmp     cpu_except
  2029                                  exc17:
  2030                                  	; [esp] = Error code
  2031 00000BA8 6A11                            push 	dword 17
  2032 00000BAA EB38                    	jmp	short cpu_except_en
  2033                                  exc18:
  2034 00000BAC 6A12                            push 	dword 18
  2035 00000BAE EB42                    	jmp	short cpu_except
  2036                                  exc19:
  2037 00000BB0 6A13                            push 	dword 19
  2038 00000BB2 EB3E                    	jmp	short cpu_except
  2039                                  exc20:
  2040 00000BB4 6A14                            push 	dword 20
  2041 00000BB6 EB3A                    	jmp	short cpu_except
  2042                                  exc21:
  2043 00000BB8 6A15                            push 	dword 21
  2044 00000BBA EB36                    	jmp	short cpu_except
  2045                                  exc22:
  2046 00000BBC 6A16                            push 	dword 22
  2047 00000BBE EB32                    	jmp	short cpu_except
  2048                                  exc23:
  2049 00000BC0 6A17                            push 	dword 23
  2050 00000BC2 EB2E                    	jmp	short cpu_except
  2051                                  exc24:
  2052 00000BC4 6A18                            push 	dword 24
  2053 00000BC6 EB2A                    	jmp	short cpu_except
  2054                                  exc25:
  2055 00000BC8 6A19                            push 	dword 25
  2056 00000BCA EB26                    	jmp	short cpu_except
  2057                                  exc26:
  2058 00000BCC 6A1A                            push 	dword 26
  2059 00000BCE EB22                    	jmp	short cpu_except
  2060                                  exc27:
  2061 00000BD0 6A1B                            push 	dword 27
  2062 00000BD2 EB1E                    	jmp	short cpu_except
  2063                                  exc28:
  2064 00000BD4 6A1C                            push 	dword 28
  2065 00000BD6 EB1A                    	jmp	short cpu_except
  2066                                  exc29:
  2067 00000BD8 6A1D                            push 	dword 29
  2068 00000BDA EB16                    	jmp	short cpu_except
  2069                                  exc30:
  2070 00000BDC 6A1E                            push 	dword 30
  2071 00000BDE EB04                    	jmp	short cpu_except_en
  2072                                  exc31:
  2073 00000BE0 6A1F                            push 	dword 31
  2074 00000BE2 EB0E                            jmp     short cpu_except
  2075                                  
  2076                                  	; 19/10/2015
  2077                                  	; 19/09/2015
  2078                                  	; 01/09/2015
  2079                                  	; 28/08/2015
  2080                                  	; 28/08/2014
  2081                                  cpu_except_en:
  2082 00000BE4 87442404                	xchg	eax, [esp+4] ; Error code
  2083 00000BE8 36A3[78050300]          	mov	[ss:error_code], eax
  2084 00000BEE 58                      	pop	eax  ; Exception number
  2085 00000BEF 870424                  	xchg	eax, [esp]
  2086                                  		; eax = eax before exception
  2087                                  		; [esp] -> exception number
  2088                                  		; [esp+4] -> EIP to return
  2089                                  	; 22/01/2017
  2090                                  	; 19/10/2015
  2091                                  	; 19/09/2015
  2092                                  	; 01/09/2015
  2093                                  	; 28/08/2015
  2094                                  	; 29/08/2014
  2095                                  	; 28/08/2014
  2096                                  	; 25/08/2014
  2097                                  	; 21/08/2014
  2098                                  cpu_except:	; CPU Exceptions
  2099 00000BF2 FC                      	cld
  2100 00000BF3 870424                  	xchg	eax, [esp] 
  2101                                  		; eax = Exception number
  2102                                  		; [esp] = eax (before exception)	
  2103 00000BF6 53                      	push	ebx
  2104 00000BF7 56                      	push	esi
  2105 00000BF8 57                      	push	edi
  2106 00000BF9 1E                      	push 	ds
  2107 00000BFA 06                      	push 	es
  2108                                  	; 28/08/2015
  2109 00000BFB 66BB1000                	mov	bx, KDATA
  2110 00000BFF 8EDB                    	mov	ds, bx
  2111 00000C01 8EC3                    	mov	es, bx
  2112 00000C03 0F20DB                  	mov	ebx, cr3
  2113 00000C06 53                      	push	ebx ; (*) page directory
  2114                                  	; 19/10/2015
  2115 00000C07 FC                      	cld
  2116                                  	; 25/03/2015
  2117 00000C08 8B1D[805E0100]          	mov	ebx, [k_page_dir]
  2118 00000C0E 0F22DB                  	mov	cr3, ebx
  2119                                  	; 28/08/2015
  2120 00000C11 83F80E                  	cmp	eax, 0Eh ; 14, PAGE FAULT	
  2121 00000C14 750F                    	jne	short cpu_except_nfp
  2122 00000C16 E8A2490000              	call	page_fault_handler
  2123 00000C1B 21C0                    	and 	eax, eax
  2124 00000C1D 0F8401010000                    jz	iiretp ; 01/09/2015
  2125 00000C23 B00E                    	mov	al, 0Eh ; 14
  2126                                  cpu_except_nfp:
  2127                                  	; 23/08/2016
  2128 00000C25 803D[7A660000]03        	cmp	byte [CRT_MODE], 3
  2129 00000C2C 7409                    	je	short cpu_except_mode_3
  2130 00000C2E 50                      	push	eax
  2131 00000C2F B003                    	mov	al, 3
  2132 00000C31 E8310D0000              	call	_set_mode
  2133 00000C36 58                      	pop	eax
  2134                                  cpu_except_mode_3:
  2135                                  	; 02/04/2015
  2136 00000C37 BB[82080000]            	mov	ebx, hang
  2137 00000C3C 875C241C                	xchg	ebx, [esp+28]
  2138                                  		; EIP (points to instruction which faults)
  2139                                  	  	; New EIP (hang)
  2140 00000C40 891D[7C050300]          	mov	[FaultOffset], ebx
  2141 00000C46 C744242008000000        	mov	dword [esp+32], KCODE ; kernel's code segment
  2142 00000C4E 814C242400020000        	or	dword [esp+36], 200h ; enable interrupts (set IF)
  2143                                  	;
  2144 00000C56 88C4                    	mov	ah, al
  2145 00000C58 240F                    	and	al, 0Fh
  2146 00000C5A 3C09                    	cmp	al, 9
  2147 00000C5C 7602                    	jna	short h1ok
  2148 00000C5E 0407                    	add	al, 'A'-':'
  2149                                  h1ok:
  2150 00000C60 C0EC04                  	shr	ah, 4
  2151 00000C63 80FC09                  	cmp	ah, 9
  2152 00000C66 7603                    	jna	short h2ok
  2153 00000C68 80C407                  	add	ah, 'A'-':'
  2154                                  h2ok:	
  2155 00000C6B 86E0                    	xchg 	ah, al	
  2156 00000C6D 66053030                	add	ax, '00'
  2157 00000C71 66A3[941E0100]          	mov	[excnstr], ax
  2158                                  	;
  2159                                  	; 29/08/2014
  2160 00000C77 A1[7C050300]            	mov	eax, [FaultOffset]
  2161 00000C7C 51                      	push	ecx
  2162 00000C7D 52                      	push	edx
  2163 00000C7E 89E3                    	mov	ebx, esp
  2164                                  	; 28/08/2015
  2165 00000C80 B910000000              	mov	ecx, 16	  ; divisor value to convert binary number
  2166                                  			  ; to hexadecimal string
  2167                                  	;mov	ecx, 10	    ; divisor to convert	
  2168                                  			    ; binary number to decimal string
  2169                                  b2d1:
  2170 00000C85 31D2                    	xor	edx, edx
  2171 00000C87 F7F1                    	div	ecx
  2172 00000C89 6652                    	push	dx
  2173 00000C8B 39C8                    	cmp	eax, ecx
  2174 00000C8D 73F6                    	jnb	short b2d1
  2175 00000C8F BF[9F1E0100]            	mov	edi, EIPstr ; EIP value
  2176                                  			    ; points to instruction which faults	
  2177                                  	; 28/08/2015
  2178 00000C94 89C2                    	mov	edx, eax
  2179                                  b2d2:
  2180                                  	;add	al, '0'
  2181 00000C96 8A82[323A0000]          	mov	al, [edx+hexchrs]
  2182 00000C9C AA                      	stosb		    ; write hexadecimal digit to its place	
  2183 00000C9D 39E3                    	cmp	ebx, esp
  2184 00000C9F 7606                    	jna	short b2d3
  2185 00000CA1 6658                    	pop	ax
  2186 00000CA3 88C2                    	mov	dl, al
  2187 00000CA5 EBEF                    	jmp	short b2d2
  2188                                  b2d3:
  2189 00000CA7 B068                    	mov 	al, 'h' ; 28/08/2015
  2190 00000CA9 AA                      	stosb
  2191 00000CAA B020                    	mov	al, 20h	    ; space
  2192 00000CAC AA                      	stosb
  2193 00000CAD 30C0                    	xor	al, al	    ; to do it an ASCIIZ string	
  2194 00000CAF AA                      	stosb
  2195                                  	;
  2196 00000CB0 5A                      	pop	edx
  2197 00000CB1 59                      	pop	ecx
  2198                                  	;
  2199 00000CB2 B44F                    	mov	ah, 4Fh	; red (4) background, 
  2200                                  			; white (F) forecolor
  2201 00000CB4 BE[841E0100]            	mov	esi, exc_msg ; message offset
  2202                                  	;
  2203                                  	; 20/01/2017 (!cpu exception!)
  2204                                  	;
  2205 00000CB9 8105[3C1C0100]A000-             add    dword [scr_row], 0A0h
  2205 00000CC1 0000               
  2206 00000CC3 8B3D[3C1C0100]                  mov    edi, [scr_row]
  2207                                  	;	
  2208 00000CC9 C605[5B030300]00        	mov	byte [sysflg], 0  ; system mode
  2209 00000CD0 FB                              sti
  2210                                  	;
  2211 00000CD1 E8EBFBFFFF              	call 	printk
  2212                                  	;
  2213 00000CD6 B410                    	mov	ah, 10h
  2214 00000CD8 E87D010000              	call	int16h ; getc
  2215                                  	;
  2216 00000CDD B003                    	mov	al, 3
  2217 00000CDF E8830C0000              	call	_set_mode
  2218                                  	;
  2219 00000CE4 B801000000              	mov	eax, 1
  2220 00000CE9 E933C40000              	jmp	sysexit ; terminate process !!!
  2221                                  	
  2222                                  	; 22/01/2017
  2223                                  	; 18/04/2016
  2224                                  	; 28/08/2015
  2225                                  	; 23/02/2015
  2226                                  	; 20/08/2014
  2227                                  ignore_int:
  2228 00000CEE 50                      	push	eax
  2229 00000CEF 53                      	push	ebx ; 23/02/2015
  2230 00000CF0 56                      	push	esi
  2231 00000CF1 57                      	push	edi
  2232 00000CF2 1E                      	push 	ds
  2233 00000CF3 06                      	push 	es
  2234                                  	; 18/04/2016
  2235 00000CF4 66B81000                	mov	ax, KDATA
  2236 00000CF8 8ED8                    	mov	ds, ax
  2237 00000CFA 8EC0                    	mov	es, ax
  2238                                  	; 28/08/2015
  2239 00000CFC 0F20D8                  	mov	eax, cr3
  2240 00000CFF 50                      	push	eax ; (*) page directory
  2241                                  	;
  2242 00000D00 B467                    	mov	ah, 67h	; brown (6) background, 
  2243                                  			; light gray (7) forecolor
  2244 00000D02 BE[4C1D0100]            	mov	esi, int_msg ; message offset
  2245                                  piemsg:
  2246                                          ; 27/08/2014
  2247 00000D07 8105[3C1C0100]A000-             add     dword [scr_row], 0A0h
  2247 00000D0F 0000               
  2248 00000D11 8B3D[3C1C0100]                  mov     edi, [scr_row]
  2249                                          ;
  2250 00000D17 E8A5FBFFFF              	call 	printk
  2251                                  	;
  2252                                  	; 23/02/2015
  2253 00000D1C B020                    	mov	al, 20h  ; END OF INTERRUPT COMMAND TO
  2254 00000D1E E6A0                    	out	0A0h, al ; the 2nd 8259
  2255                                  	; 22/08/2014
  2256 00000D20 B020                    	mov	al, 20h ; END OF INTERRUPT COMMAND TO 8259
  2257 00000D22 E620                    	out	20h, al	; 8259 PORT
  2258                                  iiretp: 
  2259                                  	; 22/01/2017
  2260                                  	; 01/09/2015
  2261                                  	; 28/08/2015
  2262 00000D24 58                      	pop	eax ; (*) page directory
  2263 00000D25 0F22D8                  	mov	cr3, eax
  2264                                  iiret:
  2265 00000D28 07                      	pop	es
  2266 00000D29 1F                      	pop	ds
  2267 00000D2A 5F                      	pop	edi
  2268 00000D2B 5E                      	pop	esi
  2269 00000D2C 5B                      	pop	ebx ; 29/08/2014
  2270 00000D2D 58                      	pop 	eax
  2271 00000D2E CF                      	iretd
  2272                                  
  2273                                  	; 23/05/2016
  2274                                  	; 22/08/2014
  2275                                  	; IBM PC/AT BIOS source code ----- 10/06/85 (bios.asm)
  2276                                  	; (INT 1Ah)
  2277                                  	;; Linux (v0.12) source code (main.c) by Linus Torvalds (1991)
  2278                                  time_of_day:
  2279 00000D2F E815560000              	call	UPD_IPR			; WAIT TILL UPDATE NOT IN PROGRESS
  2280 00000D34 726F                            jc      short time_of_day_retn ; 23/05/2016
  2281 00000D36 B000                    	mov	al, CMOS_SECONDS
  2282 00000D38 E827560000              	call	CMOS_READ
  2283 00000D3D A2[F05E0100]            	mov	[time_seconds], al 
  2284 00000D42 B002                    	mov	al, CMOS_MINUTES
  2285 00000D44 E81B560000              	call	CMOS_READ
  2286 00000D49 A2[F15E0100]            	mov	[time_minutes], al 
  2287 00000D4E B004                    	mov	al, CMOS_HOURS
  2288 00000D50 E80F560000              	call	CMOS_READ
  2289 00000D55 A2[F25E0100]                    mov     [time_hours], al
  2290 00000D5A B006                    	mov	al, CMOS_DAY_WEEK 
  2291 00000D5C E803560000              	call	CMOS_READ
  2292 00000D61 A2[F35E0100]            	mov	[date_wday], al
  2293 00000D66 B007                     	mov	al, CMOS_DAY_MONTH
  2294 00000D68 E8F7550000              	call	CMOS_READ
  2295 00000D6D A2[F45E0100]            	mov	[date_day], al
  2296 00000D72 B008                    	mov	al, CMOS_MONTH
  2297 00000D74 E8EB550000              	call	CMOS_READ
  2298 00000D79 A2[F55E0100]            	mov	[date_month], al
  2299 00000D7E B009                    	mov	al, CMOS_YEAR
  2300 00000D80 E8DF550000              	call	CMOS_READ
  2301 00000D85 A2[F65E0100]            	mov	[date_year], al
  2302 00000D8A B032                    	mov	al, CMOS_CENTURY
  2303 00000D8C E8D3550000              	call	CMOS_READ
  2304 00000D91 A2[F75E0100]            	mov	[date_century], al
  2305                                  	;
  2306 00000D96 B000                    	mov	al, CMOS_SECONDS
  2307 00000D98 E8C7550000              	call 	CMOS_READ
  2308 00000D9D 3A05[F05E0100]          	cmp	al, [time_seconds]
  2309 00000DA3 758A                    	jne	short time_of_day
  2310                                  
  2311                                  time_of_day_retn:
  2312 00000DA5 C3                      	retn
  2313                                  
  2314                                  	; 15/01/2017
  2315                                  	; 10/06/2016
  2316                                  	; 07/06/2016
  2317                                  	; 06/06/2016
  2318                                  	; 23/05/2016
  2319                                  rtc_p:
  2320 00000DA6 B101                    	mov	cl, 1 ; 15/01/2017
  2321 00000DA8 EB02                    	jmp	short rtc_p0
  2322                                  u_timer: 
  2323                                  	; Timer Events with 18.2 Hz Timer Ticks
  2324                                  	; (and also timer events with RTC seconds)
  2325 00000DAA 28C9                    	sub	cl, cl ; mov cl, 0 ; 15/01/2017
  2326                                  rtc_p0:
  2327                                  	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
  2328                                  	; Major Modification:
  2329                                  	; Check and Perform Timer Events (for RTC)
  2330                                  	; 25/08/2014 - 07/09/2014
  2331                                  	; Retro UNIX 386 v1:
  2332                                   	; Print Real Time Clock content
  2333                                  	
  2334                                  	; 15/01/2017
  2335 00000DAC 880D[106B0100]          	mov	byte [priority], cl ; 0 or 1 (not 2)
  2336 00000DB2 8A2D[136B0100]          	mov	ch, [timer_events]
  2337 00000DB8 20ED                    	and	ch, ch
  2338 00000DBA 7420                    	jz	short rtc_p3
  2339                                  
  2340 00000DBC BE[60040300]            	mov	esi, timer_set  ; beginning address of
  2341                                  				; timer events space
  2342                                  rtc_p1:
  2343 00000DC1 8B06                    	mov	eax, [esi]	
  2344 00000DC3 20C0                    	and	al, al ; 0 = free, >0 = process no.
  2345 00000DC5 7416                    	jz	short rtc_p4
  2346                                  	;
  2347 00000DC7 C1C810                  	ror	eax, 16
  2348                                  	; ah = response value, al = interrupt type
  2349                                  	; 15/01/2017
  2350                                  	; cl = interrupt source
  2351                                  	;       1 = RTC, 0 = PIT  	 	
  2352 00000DCA 38C8                    	cmp	al, cl 
  2353 00000DCC 750A                    	jne	short rtc_p2 ; not as requested or undefined !
  2354 00000DCE 3C01                    	cmp	al, 1 ; 1 ; RTC interrupt ?
  2355 00000DD0 7410                    	je	short rtc_p5 ; yes, check for response
  2356                                  	; 06/06/2016 - 18.2 Hz Timer Ticks
  2357 00000DD2 836E080A                	sub	dword [esi+8], 10 ; 1 tick = 10
  2358 00000DD6 7613                    	jna	short rtc_p6  ; continue for responding
  2359                                  rtc_p2:
  2360                                  	; 15/01/2017 (cl -> ch)
  2361                                  	; 07/06/2016
  2362 00000DD8 FECD                    	dec	ch    ; remain count of timer events	
  2363 00000DDA 7501                    	jnz	short rtc_p4
  2364                                  rtc_p3:	 
  2365 00000DDC C3                      	retn
  2366                                  rtc_p4:	
  2367                                  	;cmp	esi, timer_set + 240 ; 15*16 (last event)
  2368                                  	;jnb	short rtc_p3 ; end of timer event space
  2369 00000DDD 83C610                  	add	esi, 16 ; next timer event
  2370 00000DE0 EBDF                    	jmp	short rtc_p1
  2371                                  rtc_p5:	 
  2372                                  	; current timer count ; 06/06/2016 (182)
  2373 00000DE2 816E08B6000000          	sub	dword [esi+8], 182 ; 1 second (10*18.2)
  2374 00000DE9 77ED                    	ja	short rtc_p2  ; check for the next 
  2375                                  rtc_p6:	
  2376                                  	; it is the time of response! 
  2377 00000DEB 8B5E04                  	mov	ebx, [esi+4] ; set (count limit) value
  2378 00000DEE 895E08                  	mov	[esi+8], ebx ; reset count down value
  2379                                  			     ; to count limit
  2380                                  	; 19/12/2016
  2381                                  	; 10/12/2016 - timer callback modification
  2382 00000DF1 8B7E0C                  	mov	edi, [esi+12] ; response (or callback) address	
  2383 00000DF4 807E0100                	cmp	byte [esi+1], 0 ; >0 = callback
  2384 00000DF8 762A                    	jna	short rtc_p8
  2385                                  
  2386                                  	; timer callback !
  2387 00000DFA 0FB61E                  	movzx	ebx, byte [esi] ; process number (>0)
  2388 00000DFD 89D8                    	mov	eax, ebx
  2389 00000DFF C0E302                  	shl	bl, 2 ; *4
  2390 00000E02 89BB[0C010300]          	mov	[ebx+p.tcb-4], edi ; user's callback service addr
  2391 00000E08 3A05[B3030300]          	cmp	al, [u.uno]
  2392 00000E0E 7521                    	jne	short rtc_p9
  2393 00000E10 893D[D0030300]          	mov	[u.tcb], edi
  2394                                  rtc_p7:
  2395                                  	; 15/01/2017
  2396 00000E16 B002                    	mov	al, 2
  2397 00000E18 A2[106B0100]            	mov	[priority], al ; 2
  2398                                  	; 10/01/2017
  2399                                  	;mov	byte [u.pri], 2
  2400 00000E1D A2[A9030300]            	mov	[u.pri], al ; 2
  2401 00000E22 EBB4                    	jmp	short rtc_p2
  2402                                  rtc_p8:
  2403                                  	; response address is physical address of
  2404                                  	; the program's response (signal return) byte
  2405                                  	; 06/06/2016
  2406                                  	;mov	edi, [esi+12] ; response address
  2407 00000E24 8827                    	mov	[edi], ah     ; response value 
  2408                                  	;
  2409 00000E26 C1C010                  	rol	eax, 16
  2410                                  	; 15/01/2017
  2411 00000E29 3A05[B3030300]          	cmp	al, [u.uno] ; running process ?
  2412 00000E2F 74E5                    	je	short rtc_p7
  2413                                  rtc_p9:
  2414                                  	; al = process number  ; 10/06/2016
  2415 00000E31 B202                    	mov	dl, 2 ; priority, 2 = event (high)	
  2416 00000E33 E89CF00000              	call	set_run_sequence ; 19/05/2016
  2417 00000E38 EB9E                    	jmp	short rtc_p2 ; 10/06/2016
  2418                                  
  2419                                  ; Default IRQ 7 handler against spurious IRQs (from master PIC)
  2420                                  ; 25/02/2015 (source: http://wiki.osdev.org/8259_PIC)
  2421                                  default_irq7:
  2422 00000E3A 6650                    	push	ax
  2423 00000E3C B00B                    	mov	al, 0Bh  ; In-Service register
  2424 00000E3E E620                    	out	20h, al
  2425 00000E40 EB00                            jmp short $+2
  2426 00000E42 EB00                    	jmp short $+2
  2427 00000E44 E420                    	in	al, 20h
  2428 00000E46 2480                    	and 	al, 80h ; bit 7 (is it real IRQ 7 or fake?)
  2429 00000E48 7404                            jz      short irq7_iret ; Fake (spurious) IRQ, do not send EOI 
  2430 00000E4A B020                            mov     al, 20h ; EOI
  2431 00000E4C E620                    	out	20h, al 
  2432                                  irq7_iret:
  2433 00000E4E 6658                    	pop	ax
  2434 00000E50 CF                      	iretd
  2435                                  	
  2436                                  bcd_to_ascii:
  2437                                  	; 25/08/2014
  2438                                  	; INPUT ->
  2439                                  	;	al = Packed BCD number
  2440                                  	; OUTPUT ->
  2441                                  	;	ax  = ASCII word/number
  2442                                  	;
  2443                                  	; Erdogan Tan - 1998 (proc_hex) - TRDOS.ASM (2004-2011)
  2444                                  	;
  2445 00000E51 D410                    	db 0D4h,10h                     ; Undocumented inst. AAM
  2446                                  					; AH = AL / 10h
  2447                                  					; AL = AL MOD 10h
  2448 00000E53 660D3030                	or ax,'00'                      ; Make it ASCII based
  2449                                  
  2450 00000E57 86E0                            xchg ah, al 
  2451                                  	
  2452 00000E59 C3                      	retn	
  2453                                  	
  2454                                  
  2455                                  %include 'keyboard.s' ; 07/03/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - keyboard.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 15/01/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 17/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; keyboard.inc (17/10/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - KEYBOARD.INC
    20                              <1> ; Last Modification: 17/10/2015
    21                              <1> ;		    (Keyboard Data is in 'KYBDATA.INC')	
    22                              <1> ;
    23                              <1> ; ///////// KEYBOARD FUNCTIONS (PROCEDURES) ///////////////
    24                              <1> 
    25                              <1> ; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
    26                              <1> 
    27                              <1> ; 03/12/2014
    28                              <1> ; 26/08/2014
    29                              <1> ; KEYBOARD I/O
    30                              <1> ; (INT_16h - Retro UNIX 8086 v1 - U9.ASM, 30/06/2014)
    31                              <1> 
    32                              <1> ;NOTE: 'k0' to 'k7' are name of OPMASK registers.
    33                              <1> ;	(The reason of using '_k' labels!!!) (27/08/2014)    
    34                              <1> ;NOTE: 'NOT' keyword is '~' unary operator in NASM.
    35                              <1> ;	('NOT LC_HC' --> '~LC_HC') (bit reversing operator)
    36                              <1> 
    37                              <1> int16h:	; 30/06/2015
    38                              <1> ;getc:
    39 00000E5A 9C                  <1> 	pushfd	; 28/08/2014
    40 00000E5B 0E                  <1> 	push 	cs
    41 00000E5C E801000000          <1> 	call 	KEYBOARD_IO_1 ; getc_int
    42 00000E61 C3                  <1> 	retn	
    43                              <1> 
    44                              <1> getc_int:
    45                              <1> 	; 28/02/2015
    46                              <1> 	; 03/12/2014 (derivation from pc-xt-286 bios source code -1986-, 
    47                              <1> 	;	      instead of pc-at bios - 1985-)
    48                              <1> 	; 28/08/2014 (_k1d)
    49                              <1> 	; 30/06/2014
    50                              <1> 	; 03/03/2014
    51                              <1> 	; 28/02/2014
    52                              <1> 	; Derived from "KEYBOARD_IO_1" procedure of IBM "pc-xt-286" 
    53                              <1> 	; rombios source code (21/04/1986)
    54                              <1> 	;	 'keybd.asm', INT 16H, KEYBOARD_IO
    55                              <1> 	;
    56                              <1> 	; KYBD --- 03/06/86  KEYBOARD BIOS
    57                              <1> 	;
    58                              <1> 	;--- INT 16 H -----------------------------------------------------------------
    59                              <1> 	; KEYBOARD I/O								      :
    60                              <1> 	;	THESE ROUTINES PROVIDE READ KEYBOARD SUPPORT			      :
    61                              <1> 	; INPUT									      :
    62                              <1> 	;	(AH)= 00H  READ THE NEXT ASCII CHARACTER ENTERED FROM THE KEYBOARD,   :
    63                              <1> 	;		   RETURN THE RESULT IN (AL), SCAN CODE IN (AH).              :
    64                              <1> 	;		   THIS IS THE COMPATIBLE READ INTERFACE, EQUIVALENT TO THE   :
    65                              <1> 	;                  STANDARD PC OR PCAT KEYBOARD				      :	
    66                              <1> 	;-----------------------------------------------------------------------------:
    67                              <1> 	;	(AH)= 01H  SET THE ZERO FLAG TO INDICATE IF AN ASCII CHARACTER IS     :
    68                              <1> 	;		   AVAILABLE TO BE READ FROM THE KEYBOARD BUFFER.	      :
    69                              <1> 	;		   (ZF)= 1 -- NO CODE AVAILABLE			              :
    70                              <1> 	;		   (ZF)= 0 -- CODE IS AVAILABLE  (AX)= CHARACTER              :
    71                              <1> 	;		   IF (ZF)= 0, THE NEXT CHARACTER IN THE BUFFER TO BE READ IS :
    72                              <1> 	;		   IN (AX), AND THE ENTRY REMAINS IN THE BUFFER.              :
    73                              <1> 	;		   THIS WILL RETURN ONLY PC/PCAT KEYBOARD COMPATIBLE CODES    :
    74                              <1> 	;-----------------------------------------------------------------------------:	
    75                              <1> 	;	(AH)= 02H  RETURN THE CURRENT SHIFT STATUS IN AL REGISTER             :
    76                              <1> 	;		   THE BIT SETTINGS FOR THIS CODE ARE INDICATED IN THE        :
    77                              <1> 	;		   EQUATES FOR @KB_FLAG		                              :
    78                              <1> 	;-----------------------------------------------------------------------------:	
    79                              <1> 	;	(AH)= 03H  SET TYPAMATIC RATE AND DELAY                               :
    80                              <1> 	;	      (AL) = 05H                                                      :
    81                              <1> 	;	      (BL) = TYPAMATIC RATE (BITS 5 - 7 MUST BE RESET TO 0)           :
    82                              <1> 	;		       							      :
    83                              <1> 	;                     REGISTER     RATE      REGISTER     RATE                :
    84                              <1> 	;                      VALUE     SELECTED     VALUE     SELECTED              :
    85                              <1> 	;                     --------------------------------------------            :
    86                              <1> 	;			00H        30.0        10H        7.5                 :
    87                              <1> 	;			01H        26.7        11H        6.7                 :
    88                              <1> 	;			02H        24.0        12H        6.0                 :
    89                              <1> 	;			03H        21.8        13H        5.5                 :
    90                              <1> 	;			04H        20.0        14H        5.0                 :
    91                              <1> 	;			05H        18.5        15H        4.6                 :
    92                              <1> 	;			06H        17.1        16H        4.3                 :
    93                              <1> 	;			07H        16.0        17H        4.0                 :
    94                              <1> 	;			08H        15.0        18H        3.7                 :
    95                              <1> 	;			09H        13.3        19H        3.3                 :
    96                              <1> 	;			0AH        12.0        1AH        3.0                 :
    97                              <1> 	;			0BH        10.9        1BH        2.7                 :
    98                              <1>         ;			0CH        10.0        1CH        2.5                 :
    99                              <1> 	;			0DH         9.2        1DH        2.3                 :
   100                              <1> 	;			0EH         8.6        1EH        2.1                 :
   101                              <1> 	;			0FH         8.0        1FH        2.0                 :
   102                              <1> 	;									      :
   103                              <1> 	;	      (BH) = TYPAMATIC DELAY  (BITS 2 - 7 MUST BE RESET TO 0)         :
   104                              <1> 	;		       							      :
   105                              <1> 	;                     REGISTER     DELAY                                      :
   106                              <1> 	;                      VALUE       VALUE                                      :
   107                              <1> 	;                     ------------------                                      :
   108                              <1> 	;			00H        250 ms                                     :
   109                              <1> 	;			01H        500 ms                                     :
   110                              <1> 	;			02H        750 ms                                     :
   111                              <1> 	;			03H       1000 ms                                     :
   112                              <1> 	;-----------------------------------------------------------------------------:
   113                              <1> 	;	(AH)= 05H  PLACE ASCII CHARACTER/SCAN CODE COMBINATION IN KEYBOARD    :
   114                              <1> 	;		   BUFFER AS IF STRUCK FROM KEYBOARD                          :
   115                              <1> 	;		   ENTRY:  (CL) = ASCII CHARACTER		              :
   116                              <1> 	;		           (CH) = SCAN CODE                                   :
   117                              <1> 	;		   EXIT:   (AH) = 00H = SUCCESSFUL OPERATION                  :
   118                              <1> 	;		           (AL) = 01H = UNSUCCESSFUL - BUFFER FULL            :
   119                              <1> 	;		   FLAGS:  CARRY IF ERROR                                     :
   120                              <1> 	;-----------------------------------------------------------------------------:		
   121                              <1> 	;	(AH)= 10H  EXTENDED READ INTERFACE FOR THE ENHANCED KEYBOARD,         :
   122                              <1> 	;		   OTHERWISE SAME AS FUNCTION AH=0                            :
   123                              <1> 	;-----------------------------------------------------------------------------:
   124                              <1> 	;	(AH)= 11H  EXTENDED ASCII STATUS FOR THE ENHANCED KEYBOARD,           :
   125                              <1> 	;		   OTHERWISE SAME AS FUNCTION AH=1                            :
   126                              <1> 	;-----------------------------------------------------------------------------:	
   127                              <1> 	;	(AH)= 12H  RETURN THE EXTENDED SHIFT STATUS IN AX REGISTER            :
   128                              <1> 	;		   AL = BITS FROM KB_FLAG, AH = BITS FOR LEFT AND RIGHT       :
   129                              <1> 	;		   CTL AND ALT KEYS FROM KB_FLAG_1 AND KB_FLAG_3              :
   130                              <1> 	; OUTPUT					                              :
   131                              <1> 	;	AS NOTED ABOVE, ONLY (AX) AND FLAGS CHANGED	                      :
   132                              <1> 	;	ALL REGISTERS RETAINED		                                      :
   133                              <1> 	;------------------------------------------------------------------------------
   134                              <1> 
   135                              <1> ; 15/01/2017
   136                              <1> ; 14/01/2017
   137                              <1> ; 02/01/2017
   138                              <1> ; 29/05/2016
   139                              <1> ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   140                              <1> int32h:  ; Keyboard BIOS
   141                              <1> 
   142                              <1> KEYBOARD_IO_1:	
   143                              <1> 	;sti				; INTERRUPTS BACK ON
   144                              <1> 	; 29/05/2016
   145 00000E62 80642408BE          <1>         and     byte [esp+8], 10111110b ; clear zero flag and cary flag
   146                              <1> 	;
   147 00000E67 1E                  <1> 	push	ds			; SAVE CURRENT DS
   148 00000E68 53                  <1> 	push	ebx			; SAVE BX TEMPORARILY
   149                              <1> 	;push	ecx			; SAVE CX TEMPORARILY
   150 00000E69 66BB1000            <1>         mov     bx, KDATA 
   151 00000E6D 8EDB                <1> 	mov	ds, bx			; PUT SEGMENT VALUE OF DATA AREA INTO DS
   152                              <1> 
   153                              <1> 	; 14/01/2017
   154 00000E6F 8B1C24              <1> 	mov	ebx, [esp]
   155                              <1> 	;; 15/01/2017
   156                              <1> 	; 02/01/2017
   157                              <1> 	;;mov	byte [intflg], 32h	; keyboard interrupt 
   158 00000E72 FB                  <1> 	sti
   159                              <1> 	;
   160                              <1> 
   161 00000E73 08E4                <1> 	or	ah, ah			; CHECK FOR (AH)= 00H
   162 00000E75 743A                <1> 	jz	short _K1		; ASCII_READ
   163 00000E77 FECC                <1> 	dec	ah                      ; CHECK FOR (AH)= 01H
   164 00000E79 7453                <1>         jz      short _K2               ; ASCII_STATUS
   165 00000E7B FECC                <1> 	dec	ah			; CHECK FOR (AH)= 02H
   166 00000E7D 0F8494000000        <1>         jz      _K3                     ; SHIFT STATUS
   167 00000E83 FECC                <1> 	dec	ah			; CHECK FOR (AH)= 03H	
   168 00000E85 0F8493000000        <1>         jz      _K300                   ; SET TYPAMATIC RATE/DELAY
   169 00000E8B 80EC02              <1> 	sub	ah, 2			; CHECK FOR (AH)= 05H	
   170 00000E8E 0F84BC000000        <1>         jz      _K500                   ; KEYBOARD WRITE         
   171                              <1> _KIO1:	
   172 00000E94 80EC0B              <1> 	sub	ah, 11			; AH =  10H
   173 00000E97 740C                <1> 	jz	short _K1E		; EXTENDED ASCII READ
   174 00000E99 FECC                <1> 	dec	ah			; CHECK FOR (AH)= 11H
   175 00000E9B 7422                <1> 	jz	short _K2E		; EXTENDED_ASCII_STATUS
   176 00000E9D FECC                <1> 	dec	ah			; CHECK FOR (AH)= 12H
   177 00000E9F 7458                <1> 	jz	short _K3E		; EXTENDED_SHIFT_STATUS
   178                              <1> _KIO_EXIT:
   179                              <1> 	; 02/01/2017
   180 00000EA1 FA                  <1> 	cli
   181                              <1> 	;;mov	byte [intflg], 0 ;; 15/01/2017
   182                              <1> 	;
   183                              <1> 	;pop	ecx			; RECOVER REGISTER
   184 00000EA2 5B                  <1> 	pop	ebx			; RECOVER REGISTER
   185 00000EA3 1F                  <1> 	pop	ds			; RECOVER SEGMENT
   186 00000EA4 CF                  <1> 	iretd				; INVALID COMMAND, EXIT
   187                              <1> 
   188                              <1> 	;-----	ASCII CHARACTER
   189                              <1> _K1E:	
   190 00000EA5 E8D3000000          <1> 	call	_K1S			; GET A CHARACTER FROM THE BUFFER (EXTENDED)
   191 00000EAA E848010000          <1> 	call	_KIO_E_XLAT		; ROUTINE TO XLATE FOR EXTENDED CALLS
   192 00000EAF EBF0                <1> 	jmp	short _KIO_EXIT         ; GIVE IT TO THE CALLER
   193                              <1> _K1:	
   194 00000EB1 E8C7000000          <1> 	call	_K1S			; GET A CHARACTER FROM THE BUFFER
   195 00000EB6 E847010000          <1> 	call	_KIO_S_XLAT		; ROUTINE TO XLATE FOR STANDARD CALLS
   196 00000EBB 72F4                <1> 	jc	short _K1		; CARRY SET MEANS TROW CODE AWAY
   197                              <1> _K1A:
   198 00000EBD EBE2                <1> 	jmp	short _KIO_EXIT         ; RETURN TO CALLER
   199                              <1> 
   200                              <1> 	;-----	ASCII STATUS
   201                              <1> _K2E:	
   202 00000EBF E804010000          <1> 	call	_K2S			; TEST FOR CHARACTER IN BUFFER (EXTENDED)
   203 00000EC4 7420                <1> 	jz	short _K2B		; RETURN IF BUFFER EMPTY
   204 00000EC6 9C                  <1> 	pushf				; SAVE ZF FROM TEST
   205 00000EC7 E82B010000          <1> 	call	_KIO_E_XLAT		; ROUTINE TO XLATE FOR EXTENDED CALLS
   206 00000ECC EB17                <1> 	jmp	short _K2A	        ; GIVE IT TO THE CALLER
   207                              <1> _K2:	
   208 00000ECE E8F5000000          <1> 	call	_K2S			; TEST FOR CHARACTER IN BUFFER
   209 00000ED3 7411                <1> 	jz	short _K2B		; RETURN IF BUFFER EMPTY
   210 00000ED5 9C                  <1> 	pushf				; SAVE ZF FROM TEST
   211 00000ED6 E827010000          <1> 	call	_KIO_S_XLAT		; ROUTINE TO XLATE FOR STANDARD CALLS
   212 00000EDB 7308                <1> 	jnc	short _K2A	        ; CARRY CLEAR MEANS PASS VALID CODE
   213 00000EDD 9D                  <1> 	popf				; INVALID CODE FOR THIS TYPE OF CALL
   214 00000EDE E89A000000          <1> 	call	_K1S			; THROW THE CHARACTER AWAY
   215 00000EE3 EBE9                <1> 	jmp	short _K2		; GO LOOK FOR NEXT CHAR, IF ANY
   216                              <1> _K2A:
   217 00000EE5 9D                  <1> 	popf				; RESTORE ZF FROM TEST
   218                              <1> _K2B:
   219                              <1> 	; 02/01/2017
   220 00000EE6 FA                  <1> 	cli
   221                              <1> 	;; mov	byte [intflg], 0 ;; 15/01/2017
   222                              <1> 	;
   223                              <1> 	;pop	ecx			; RECOVER REGISTER
   224 00000EE7 5B                  <1> 	pop	ebx			; RECOVER REGISTER
   225 00000EE8 1F                  <1> 	pop	ds			; RECOVER SEGMENT
   226                              <1> 	; (*) 29/05/2016
   227                              <1> 	; (*) retf 4			; THROW AWAY (e)FLAGS
   228 00000EE9 7208                <1> 	jc	short _k2d
   229 00000EEB 7505                <1> 	jnz	short _k2c
   230 00000EED 804C240840          <1> 	or	byte [esp+8], 01000000b	; set zero flag bit of eflags register
   231                              <1> _k2c:
   232 00000EF2 CF                  <1> 	iretd
   233                              <1> _k2d:
   234                              <1> 	; 29/05/2016 -set carry flag on stack-
   235                              <1> 	; [esp] = EIP
   236                              <1> 	; [esp+4] = CS
   237                              <1> 	; [esp+8] = E-FLAGS
   238 00000EF3 804C240801          <1> 	or	byte [esp+8], 1  ; set carry bit of eflags register
   239                              <1> 	; [esp+12] = ESP (user)
   240                              <1> 	; [esp+16] = SS (User)
   241 00000EF8 CF                  <1> 	iretd
   242                              <1> 
   243                              <1> 	
   244                              <1> 	; (*) 29/05/2016 - 'ref 4' intruction causes to stack fault
   245                              <1> 	; (OUTER-PRIVILEGE-LEVEL)
   246                              <1> 	; INTEL 80386 PROGRAMMER'S REFERENCE MANUAL 1986
   247                              <1> 	; // RETF instruction:
   248                              <1> 	;
   249                              <1> 	; IF OperandMode=32 THEN
   250                              <1>  	;    Load CS:EIP from stack;
   251                              <1>  	;    Set CS RPL to CPL;
   252                              <1>  	;    Increment eSP by 8 plus the immediate offset if it exists;
   253                              <1>  	;    Load SS:eSP from stack;
   254                              <1>  	; ELSE (* OperandMode=16 *)
   255                              <1>  	;    Load CS:IP from stack;
   256                              <1>  	;    Set CS RPL to CPL;
   257                              <1>  	;    Increment eSP by 4 plus the immediate offset if it exists;
   258                              <1> 	;    Load SS:eSP from stack;
   259                              <1>  	; FI;
   260                              <1> 	;
   261                              <1> 	; //
   262                              <1> 
   263                              <1> 	;-----	SHIFT STATUS
   264                              <1> _K3E:                                   ; GET THE EXTENDED SHIFT STATUS FLAGS
   265 00000EF9 8A25[46660000]      <1> 	mov	ah, [KB_FLAG_1]		; GET SYSTEM SHIFT KEY STATUS
   266 00000EFF 80E404              <1> 	and	ah, SYS_SHIFT		; MASK ALL BUT SYS KEY BIT
   267                              <1> 	;mov	cl, 5			; SHIFT THEW SYSTEMKEY BIT OVER TO
   268                              <1> 	;shl	ah, cl			; BIT 7 POSITION
   269 00000F02 C0E405              <1>         shl	ah, 5
   270 00000F05 A0[46660000]        <1> 	mov	al, [KB_FLAG_1]		; GET SYSTEM SHIFT STATES BACK
   271 00000F0A 2473                <1> 	and	al, 01110011b		; ELIMINATE SYS SHIFT, HOLD_STATE AND INS_SHIFT
   272 00000F0C 08C4                <1> 	or	ah, al                  ; MERGE REMAINING BITS INTO AH
   273 00000F0E A0[48660000]        <1> 	mov	al, [KB_FLAG_3]		; GET RIGHT CTL AND ALT
   274 00000F13 240C                <1> 	and	al, 00001100b		; ELIMINATE LC_E0 AND LC_E1
   275 00000F15 08C4                <1> 	or	ah, al			; OR THE SHIFT FLAGS TOGETHER
   276                              <1> _K3:
   277 00000F17 A0[45660000]        <1> 	mov	al, [KB_FLAG]		; GET THE SHIFT STATUS FLAGS
   278                              <1> 	;jmp	short _KIO_EXIT		; RETURN TO CALLER
   279 00000F1C EB83                <1> 	jmp	_KIO_EXIT
   280                              <1> 
   281                              <1> 	;-----	SET TYPAMATIC RATE AND DELAY
   282                              <1> _K300:
   283 00000F1E 3C05                <1> 	cmp	al, 5			; CORRECT FUNCTION CALL?
   284                              <1> 	;jne	short _KIO_EXIT		; NO, RETURN
   285 00000F20 0F857BFFFFFF        <1>      	jne	_KIO_EXIT
   286 00000F26 F6C3E0              <1> 	test	bl, 0E0h		; TEST FOR OUT-OF-RANGE RATE
   287 00000F29 0F8572FFFFFF        <1>         jnz     _KIO_EXIT               ; RETURN IF SO
   288 00000F2F F6C7FC              <1> 	test	BH, 0FCh		; TEST FOR OUT-OF-RANGE DELAY
   289 00000F32 0F8569FFFFFF        <1>         jnz     _KIO_EXIT               ; RETURN IF SO
   290 00000F38 B0F3                <1> 	mov	al, KB_TYPA_RD		; COMMAND FOR TYPAMATIC RATE/DELAY		
   291 00000F3A E8DA060000          <1> 	call	SND_DATA		; SEND TO KEYBOARD	
   292                              <1> 	;mov	cx, 5			; SHIFT COUNT
   293                              <1> 	;shl	bh, cl			; SHIFT DELAY OVER
   294 00000F3F C0E705              <1> 	shl	bh, 5
   295 00000F42 88D8                <1> 	mov	al, bl			; PUT IN RATE
   296 00000F44 08F8                <1> 	or	al, bh			; AND DELAY
   297 00000F46 E8CE060000          <1> 	call	SND_DATA		; SEND TO KEYBOARD	
   298 00000F4B E951FFFFFF          <1>         jmp     _KIO_EXIT               ; RETURN TO CALLER
   299                              <1> 
   300                              <1> 	;-----	WRITE TO KEYBOARD BUFFER
   301                              <1> _K500:
   302 00000F50 56                  <1> 	push	esi			; SAVE SI (esi)
   303 00000F51 FA                  <1> 	cli				; 
   304 00000F52 8B1D[56660000]      <1>      	mov	ebx, [BUFFER_TAIL]	; GET THE 'IN TO' POINTER TO THE BUFFER
   305 00000F58 89DE                <1> 	mov	esi, ebx		; SAVE A COPY IN CASE BUFFER NOT FULL
   306 00000F5A E8D3000000          <1> 	call	_K4			; BUMP THE POINTER TO SEE IF BUFFER IS FULL
   307 00000F5F 3B1D[52660000]      <1> 	cmp	ebx, [BUFFER_HEAD]	; WILL THE BUFFER OVERRUN IF WE STORE THIS?
   308 00000F65 740D                <1> 	je	short _K502		; YES - INFORM CALLER OF ERROR		
   309 00000F67 66890E              <1> 	mov	[esi], cx		; NO - PUT ASCII/SCAN CODE INTO BUFFER	
   310 00000F6A 891D[56660000]      <1> 	mov	[BUFFER_TAIL], ebx	; ADJUST 'IN TO' POINTER TO REFLECT CHANGE
   311 00000F70 28C0                <1> 	sub	al, al			; TELL CALLER THAT OPERATION WAS SUCCESSFUL
   312 00000F72 EB02                <1> 	jmp	short _K504		; SUB INSTRUCTION ALSO RESETS CARRY FLAG
   313                              <1> _K502:
   314 00000F74 B001                <1> 	mov	al, 01h			; BUFFER FULL INDICATION
   315                              <1> _K504:
   316 00000F76 FB                  <1> 	sti				
   317 00000F77 5E                  <1> 	pop	esi			; RECOVER SI (esi)
   318 00000F78 E924FFFFFF          <1>         jmp     _KIO_EXIT               ; RETURN TO CALLER WITH STATUS IN AL
   319                              <1> 
   320                              <1> 	;-----	READ THE KEY TO FIGURE OUT WHAT TO DO -----
   321                              <1> _K1S:
   322 00000F7D FA                  <1> 	cli	; 03/12/2014
   323 00000F7E 8B1D[52660000]      <1>         mov     ebx, [BUFFER_HEAD] 	; GET POINTER TO HEAD OF BUFFER
   324 00000F84 3B1D[56660000]      <1>         cmp     ebx, [BUFFER_TAIL] 	; TEST END OF BUFFER
   325                              <1> 	;jne	short _K1U		; IF ANYTHING IN BUFFER SKIP INTERRUPT
   326 00000F8A 750F                <1> 	jne	short _k1x ; 03/12/2014
   327                              <1> 	;
   328                              <1> 	; 03/12/2014
   329                              <1> 	; 28/08/2014
   330                              <1> 	; PERFORM OTHER FUNCTION ?? here !
   331                              <1> 	;; MOV	AX, 9002h		; MOVE IN WAIT CODE & TYPE
   332                              <1> 	;; INT 	15H			; PERFORM OTHER FUNCTION
   333                              <1> _K1T:                                   ; ASCII READ
   334 00000F8C FB                  <1> 	sti				; INTERRUPTS BACK ON DURING LOOP
   335 00000F8D 90                  <1> 	nop				; ALLOW AN INTERRUPT TO OCCUR
   336                              <1> _K1U:	
   337 00000F8E FA                  <1> 	cli				; INTERRUPTS BACK OFF
   338 00000F8F 8B1D[52660000]      <1>         mov    	ebx, [BUFFER_HEAD] 	; GET POINTER TO HEAD OF BUFFER
   339 00000F95 3B1D[56660000]      <1>         cmp     ebx, [BUFFER_TAIL] 	; TEST END OF BUFFER
   340                              <1> _k1x:
   341 00000F9B 53                  <1> 	push	ebx			; SAVE ADDRESS		
   342 00000F9C 9C                  <1> 	pushf				; SAVE FLAGS
   343 00000F9D E82F070000          <1> 	call	MAKE_LED		; GO GET MODE INDICATOR DATA BYTE
   344 00000FA2 8A1D[47660000]      <1> 	mov	bl, [KB_FLAG_2] 	; GET PREVIOUS BITS
   345 00000FA8 30C3                <1> 	xor	bl, al			; SEE IF ANY DIFFERENT
   346 00000FAA 80E307              <1> 	and	bl, 07h	; KB_LEDS	; ISOLATE INDICATOR BITS
   347 00000FAD 7406                <1> 	jz	short _K1V		; IF NO CHANGE BYPASS UPDATE
   348 00000FAF E8C9060000          <1> 	call	SND_LED1
   349 00000FB4 FA                  <1> 	cli				; DISABLE INTERRUPTS
   350                              <1> _K1V:
   351 00000FB5 9D                  <1> 	popf				; RESTORE FLAGS
   352 00000FB6 5B                  <1> 	pop	ebx			; RESTORE ADDRESS
   353 00000FB7 74D3                <1>         je      short _K1T              ; LOOP UNTIL SOMETHING IN BUFFER
   354                              <1> 	;
   355 00000FB9 668B03              <1> 	mov	ax, [ebx] 		; GET SCAN CODE AND ASCII CODE
   356 00000FBC E871000000          <1>         call    _K4                     ; MOVE POINTER TO NEXT POSITION
   357 00000FC1 891D[52660000]      <1>         mov     [BUFFER_HEAD], ebx      ; STORE VALUE IN VARIABLE
   358 00000FC7 C3                  <1> 	retn				; RETURN
   359                              <1> 
   360                              <1> 	;-----	READ THE KEY TO SEE IF ONE IS PRESENT -----
   361                              <1> _K2S:
   362 00000FC8 FA                  <1> 	cli				; INTERRUPTS OFF
   363 00000FC9 8B1D[52660000]      <1>         mov     ebx, [BUFFER_HEAD]      ; GET HEAD POINTER
   364 00000FCF 3B1D[56660000]      <1>         cmp     ebx, [BUFFER_TAIL]      ; IF EQUAL (Z=1) THEN NOTHING THERE
   365 00000FD5 668B03              <1> 	mov	ax, [ebx]
   366 00000FD8 9C                  <1> 	pushf				; SAVE FLAGS
   367 00000FD9 6650                <1> 	push	ax			; SAVE CODE
   368 00000FDB E8F1060000          <1> 	call	MAKE_LED		; GO GET MODE INDICATOR DATA BYTE
   369 00000FE0 8A1D[47660000]      <1> 	mov	bl, [KB_FLAG_2] 	; GET PREVIOUS BITS
   370 00000FE6 30C3                <1> 	xor	bl, al			; SEE IF ANY DIFFERENT
   371 00000FE8 80E307              <1> 	and	bl, 07h ; KB_LEDS	; ISOLATE INDICATOR BITS
   372 00000FEB 7405                <1> 	jz	short _K2T		; IF NO CHANGE BYPASS UPDATE
   373 00000FED E874060000          <1> 	call	SND_LED			; GO TURN ON MODE INDICATORS
   374                              <1> _K2T:
   375 00000FF2 6658                <1> 	pop	ax			; RESTORE CODE
   376 00000FF4 9D                  <1> 	popf				; RESTORE FLAGS
   377 00000FF5 FB                  <1> 	sti				; INTERRUPTS BACK ON
   378 00000FF6 C3                  <1> 	retn				; RETURN
   379                              <1> 
   380                              <1> 	;-----	ROUTINE TO TRANSLATE SCAN CODE PAIRS FOR EXTENDED CALLS -----
   381                              <1> _KIO_E_XLAT:
   382 00000FF7 3CF0                <1> 	cmp	al, 0F0h		; IS IT ONE OF THE FILL-INs?
   383 00000FF9 7506                <1> 	jne	short _KIO_E_RET	; NO, PASS IT ON
   384 00000FFB 08E4                <1>         or 	ah, ah			; AH = 0 IS SPECIAL CASE
   385 00000FFD 7402                <1>         jz	short _KIO_E_RET        ; PASS THIS ON UNCHANGED
   386 00000FFF 30C0                <1> 	xor	al, al			; OTHERWISE SET AL = 0
   387                              <1> _KIO_E_RET:				
   388 00001001 C3                  <1> 	retn				; GO BACK
   389                              <1> 
   390                              <1> 	;-----	ROUTINE TO TRANSLATE SCAN CODE PAIRS FOR STANDARD CALLS -----
   391                              <1> _KIO_S_XLAT:
   392 00001002 80FCE0              <1> 	cmp	ah, 0E0h		; IS IT KEYPAD ENTER OR / ?
   393 00001005 750F                <1> 	jne	short _KIO_S2		; NO, CONTINUE
   394 00001007 3C0D                <1> 	cmp	al, 0Dh			; KEYPAD ENTER CODE?
   395 00001009 7408                <1>         je	short _KIO_S1		; YES, MASSAGE A BIT
   396 0000100B 3C0A                <1> 	cmp	al, 0Ah			; CTRL KEYPAD ENTER CODE?
   397 0000100D 7404                <1>         je	short _KIO_S1		; YES, MASSAGE THE SAME
   398 0000100F B435                <1> 	mov	ah, 35h			; NO, MUST BE KEYPAD /
   399                              <1> _kio_ret: ; 03/12/2014
   400 00001011 F8                  <1> 	clc
   401 00001012 C3                  <1> 	retn
   402                              <1> 	;jmp	short _KIO_USE		; GIVE TO CALLER
   403                              <1> _KIO_S1:				
   404 00001013 B41C                <1> 	mov	ah, 1Ch			; CONVERT TO COMPATIBLE OUTPUT
   405                              <1> 	;jmp	short _KIO_USE		; GIVE TO CALLER
   406 00001015 C3                  <1> 	retn
   407                              <1> _KIO_S2:		
   408 00001016 80FC84              <1> 	cmp	ah, 84h			; IS IT ONE OF EXTENDED ONES?
   409 00001019 7715                <1> 	ja	short _KIO_DIS		; YES, THROW AWAY AND GET ANOTHER CHAR
   410 0000101B 3CF0                <1> 	cmp	al, 0F0h		; IS IT ONE OF THE FILL-INs?
   411 0000101D 7506                <1>         jne	short _KIO_S3		; NO, TRY LAST TEST
   412 0000101F 08E4                <1> 	or	ah, ah			; AH = 0 IS SPECIAL CASE
   413 00001021 740C                <1>         jz	short _KIO_USE		; PASS THIS ON UNCHANGED
   414 00001023 EB0B                <1> 	jmp	short _KIO_DIS		; THROW AWAY THE REST
   415                              <1> _KIO_S3:
   416 00001025 3CE0                <1> 	cmp	al, 0E0h		; IS IT AN EXTENSION OF A PREVIOUS ONE?
   417                              <1> 	;jne	short _KIO_USE		; NO, MUST BE A STANDARD CODE
   418 00001027 75E8                <1> 	jne	short _kio_ret
   419 00001029 08E4                <1> 	or	ah, ah			; AH = 0 IS SPECIAL CASE
   420 0000102B 7402                <1>         jz	short _KIO_USE		; JUMP IF AH = 0
   421 0000102D 30C0                <1> 	xor	al, al			; CONVERT TO COMPATIBLE OUTPUT
   422                              <1> 	;jmp	short _KIO_USE		; PASS IT ON TO CALLER
   423                              <1> _KIO_USE:
   424                              <1> 	;clc				; CLEAR CARRY TO INDICATE GOOD CODE
   425 0000102F C3                  <1> 	retn				; RETURN	
   426                              <1> _KIO_DIS:
   427 00001030 F9                  <1> 	stc				; SET CARRY TO INDICATE DISCARD CODE
   428 00001031 C3                  <1> 	retn				; RETURN
   429                              <1> 
   430                              <1> 	;-----	INCREMENT BUFFER POINTER ROUTINE -----
   431                              <1> _K4:    
   432 00001032 43                  <1> 	inc     ebx
   433 00001033 43                  <1> 	inc	ebx			; MOVE TO NEXT WORD IN LIST
   434 00001034 3B1D[4E660000]      <1>         cmp     ebx, [BUFFER_END] 	; AT END OF BUFFER?
   435                              <1>         ;jne    short _K5               ; NO, CONTINUE
   436 0000103A 7206                <1> 	jb	short _K5
   437 0000103C 8B1D[4A660000]      <1>         mov     ebx, [BUFFER_START]     ; YES, RESET TO BUFFER BEGINNING
   438                              <1> _K5:
   439 00001042 C3                  <1> 	retn
   440                              <1> 
   441                              <1> ; 20/02/2015
   442                              <1> ; 05/12/2014
   443                              <1> ; 26/08/2014
   444                              <1> ; KEYBOARD (HARDWARE) INTERRUPT -  IRQ LEVEL 1
   445                              <1> ; (INT_09h - Retro UNIX 8086 v1 - U9.ASM, 07/03/2014)
   446                              <1> ;
   447                              <1> ; Derived from "KB_INT_1" procedure of IBM "pc-at" 
   448                              <1> ; rombios source code (06/10/1985)
   449                              <1> ; 'keybd.asm', HARDWARE INT 09h - (IRQ Level 1)
   450                              <1> 
   451                              <1> ; EQUATES (IBM PC-XT-286 BIOS, 1986, 'POSQEQU.INC')
   452                              <1> 
   453                              <1> ;--------- 8042 COMMANDS -------------------------------------------------------
   454                              <1> ENA_KBD		equ	0AEh		; ENABLE KEYBOARD COMMAND
   455                              <1> DIS_KBD		equ	0ADh		; DISABLE KEYBOARD COMMAND
   456                              <1> SHUT_CMD	equ	0FEh		; CAUSE A SHUTDOWN COMMAND
   457                              <1> ;--------- 8042 KEYBOARD INTERFACE AND DIAGNOSTIC CONTROL REGISTERS ------------
   458                              <1> STATUS_PORT	equ	064h		; 8042 STATUS PORT
   459                              <1> INPT_BUF_FULL	equ	00000010b 	; 1 = +INPUT BUFFER FULL
   460                              <1> PORT_A		equ	060h		; 8042 KEYBOARD SCAN CODE/CONTROL PORT
   461                              <1> ;---------- 8042 KEYBOARD RESPONSE ---------------------------------------------
   462                              <1> KB_ACK		equ	0FAh		; ACKNOWLEDGE PROM TRANSMISSION
   463                              <1> KB_RESEND	equ	0FEh		; RESEND REQUEST
   464                              <1> KB_OVER_RUN	equ	0FFh		; OVER RUN SCAN CODE
   465                              <1> ;---------- KEYBOARD/LED COMMANDS ----------------------------------------------
   466                              <1> KB_ENABLE	equ	0F4h		; KEYBOARD ENABLE
   467                              <1> LED_CMD		equ	0EDh		; LED WRITE COMMAND
   468                              <1> KB_TYPA_RD	equ	0F3h		; TYPAMATIC RATE/DELAY COMMAND
   469                              <1> ;---------- KEYBOARD SCAN CODES ------------------------------------------------
   470                              <1> NUM_KEY		equ	69		; SCAN CODE FOR	 NUMBER LOCK KEY
   471                              <1> SCROLL_KEY	equ	70		; SCAN CODE FOR	 SCROLL LOCK KEY
   472                              <1> ALT_KEY		equ	56		; SCAN CODE FOR	 ALTERNATE SHIFT KEY
   473                              <1> CTL_KEY		equ	29		; SCAN CODE FOR	 CONTROL KEY
   474                              <1> CAPS_KEY	equ	58		; SCAN CODE FOR	 SHIFT LOCK KEY
   475                              <1> DEL_KEY		equ	83		; SCAN CODE FOR	 DELETE KEY
   476                              <1> INS_KEY		equ	82		; SCAN CODE FOR	 INSERT KEY
   477                              <1> LEFT_KEY	equ	42		; SCAN CODE FOR	 LEFT SHIFT
   478                              <1> RIGHT_KEY	equ	54		; SCAN CODE FOR	 RIGHT SHIFT
   479                              <1> SYS_KEY		equ	84		; SCAN CODE FOR	 SYSTEM KEY
   480                              <1> ;---------- ENHANCED KEYBOARD SCAN CODES ---------------------------------------
   481                              <1> ID_1		equ	0ABh		; 1ST ID CHARACTER FOR KBX
   482                              <1> ID_2		equ	041h		; 2ND ID CHARACTER FOR KBX
   483                              <1> ID_2A		equ	054h		; ALTERNATE 2ND ID CHARACTER FOR KBX
   484                              <1> F11_M		equ	87		; F11 KEY MAKE
   485                              <1> F12_M		equ	88		; F12 KEY MAKE
   486                              <1> MC_E0		equ	224		; GENERAL MARKER CODE
   487                              <1> MC_E1		equ	225		; PAUSE KEY MARKER CODE
   488                              <1> ;---------- FLAG EQUATES WITHIN @KB_FLAG----------------------------------------
   489                              <1> RIGHT_SHIFT	equ	00000001b	; RIGHT SHIFT KEY DEPRESSED
   490                              <1> LEFT_SHIFT	equ	00000010b	; LEFT SHIFT KEY DEPRESSED
   491                              <1> CTL_SHIFT	equ	00000100b	; CONTROL SHIFT KEY DEPRESSED
   492                              <1> ALT_SHIFT	equ	00001000b	; ALTERNATE SHIFT KEY DEPRESSED
   493                              <1> SCROLL_STATE	equ	00010000b	; SCROLL LOCK STATE IS ACTIVE
   494                              <1> NUM_STATE	equ	00100000b	; NUM LOCK STATE IS ACTIVE
   495                              <1> CAPS_STATE	equ	01000000b	; CAPS LOCK STATE IS ACTIVE
   496                              <1> INS_STATE	equ	10000000b	; INSERT STATE IS ACTIVE
   497                              <1> ;---------- FLAG EQUATES WITHIN	@KB_FLAG_1 -------------------------------------
   498                              <1> L_CTL_SHIFT	equ	00000001b	; LEFT CTL KEY DOWN
   499                              <1> L_ALT_SHIFT	equ	00000010b	; LEFT ALT KEY DOWN
   500                              <1> SYS_SHIFT	equ	00000100b	; SYSTEM KEY DEPRESSED AND HELD
   501                              <1> HOLD_STATE	equ	00001000b	; SUSPEND KEY HAS BEEN TOGGLED
   502                              <1> SCROLL_SHIFT	equ	00010000b	; SCROLL LOCK KEY IS DEPRESSED
   503                              <1> NUM_SHIFT	equ	00100000b	; NUM LOCK KEY IS DEPRESSED
   504                              <1> CAPS_SHIFT	equ	01000000b	; CAPS LOCK KEY IS DEPRE55ED
   505                              <1> INS_SHIFT	equ	10000000b	; INSERT KEY IS DEPRESSED
   506                              <1> ;---------- FLAGS EQUATES WITHIN @KB_FLAG_2 -----------------------------------
   507                              <1> KB_LEDS		equ	00000111b	; KEYBOARD LED STATE BITS
   508                              <1> ;		equ	00000001b	; SCROLL LOCK INDICATOR
   509                              <1> ;		equ	00000010b	; NUM LOCK INDICATOR
   510                              <1> ;		equ	00000100b	; CAPS LOCK INDICATOR
   511                              <1> ;		equ	00001000b	; RESERVED (MUST BE ZERO)
   512                              <1> KB_FA		equ	00010000b	; ACKNOWLEDGMENT RECEIVED
   513                              <1> KB_FE		equ	00100000b	; RESEND RECEIVED FLAG
   514                              <1> KB_PR_LED	equ	01000000b	; MODE INDICATOR UPDATE
   515                              <1> KB_ERR		equ	10000000b	; KEYBOARD TRANSMIT ERROR FLAG
   516                              <1> ;----------- FLAGS EQUATES WITHIN @KB_FLAG_3 -----------------------------------
   517                              <1> LC_E1		equ	00000001b	; LAST CODE WAS THE E1 HIDDEN CODE
   518                              <1> LC_E0		equ	00000010b	; LAST CODE WAS THE E0 HIDDEN CODE
   519                              <1> R_CTL_SHIFT	equ	00000100b	; RIGHT CTL KEY DOWN
   520                              <1> R_ALT_SHIFT	equ	00001000b	; RIGHT ALT KEY DOWN
   521                              <1> GRAPH_ON	equ	00001000b	; ALT GRAPHICS KEY DOWN (WT ONLY)	
   522                              <1> KBX		equ	00010000b	; ENHANCED KEYBOARD INSTALLED
   523                              <1> SET_NUM_LK	equ	00100000b	; FORCE NUM LOCK IF READ ID AND KBX
   524                              <1> LC_AB		equ	01000000b	; LAST CHARACTER WAS FIRST ID CHARACTER
   525                              <1> RD_ID		equ	10000000b	; DOING A READ ID (MUST BE BIT0)
   526                              <1> ;
   527                              <1> ;----------- INTERRUPT EQUATES -------------------------------------------------
   528                              <1> EOI		equ	020h		; END OF INTERRUPT COMMAND TO 8259
   529                              <1> INTA00		equ	020h		; 8259 PORT
   530                              <1> 
   531                              <1> 
   532                              <1> kb_int:
   533                              <1> 
   534                              <1> ; 17/10/2015 ('ctrlbrk') 
   535                              <1> ; 05/12/2014
   536                              <1> ; 04/12/2014 (derived from pc-xt-286 bios source code -1986-)
   537                              <1> ; 26/08/2014
   538                              <1> ;
   539                              <1> ; 03/06/86  KEYBOARD BIOS
   540                              <1> ;
   541                              <1> ;--- HARDWARE INT 09H -- (IRQ LEVEL 1) ------------------------------------------
   542                              <1> ;										;
   543                              <1> ;	KEYBOARD INTERRUPT ROUTINE						;
   544                              <1> ;										;
   545                              <1> ;--------------------------------------------------------------------------------
   546                              <1> 
   547                              <1> KB_INT_1:
   548 00001043 FB                  <1> 	sti				; ENABLE INTERRUPTS
   549                              <1> 	;push	ebp
   550 00001044 50                  <1> 	push	eax
   551 00001045 53                  <1> 	push	ebx
   552 00001046 51                  <1> 	push	ecx
   553 00001047 52                  <1> 	push	edx
   554 00001048 56                  <1> 	push	esi
   555 00001049 57                  <1> 	push	edi
   556 0000104A 1E                  <1> 	push	ds
   557 0000104B 06                  <1> 	push	es
   558 0000104C FC                  <1> 	cld				; FORWARD DIRECTION
   559 0000104D 66B81000            <1> 	mov	ax, KDATA
   560 00001051 8ED8                <1> 	mov	ds, ax
   561 00001053 8EC0                <1> 	mov	es, ax
   562                              <1> 	;
   563                              <1> 	;-----	WAIT FOR KEYBOARD DISABLE COMMAND TO BE ACCEPTED
   564 00001055 B0AD                <1> 	mov	al, DIS_KBD		; DISABLE THE KEYBOARD COMMAND
   565 00001057 E8A9050000          <1> 	call	SHIP_IT			; EXECUTE DISABLE
   566 0000105C FA                  <1> 	cli				; DISABLE INTERRUPTS
   567 0000105D B900000100          <1> 	mov	ecx, 10000h		; SET MAXIMUM TIMEOUT
   568                              <1> KB_INT_01:
   569 00001062 E464                <1> 	in	al, STATUS_PORT		; READ ADAPTER STATUS
   570 00001064 A802                <1> 	test	al, INPT_BUF_FULL	; CHECK INPUT BUFFER FULL STATUS BIT
   571 00001066 E0FA                <1> 	loopnz	KB_INT_01		; WAIT FOR COMMAND TO BE ACCEPTED
   572                              <1> 	;
   573                              <1> 	;-----	READ CHARACTER FROM KEYBOARD INTERFACE
   574 00001068 E460                <1> 	in	al, PORT_A		; READ IN THE CHARACTER
   575                              <1> 	;
   576                              <1> 	;-----	SYSTEM HOOK INT 15H - FUNCTION 4FH (ON HARDWARE INT LEVEL 9H) 	
   577                              <1> 	;MOV	AH, 04FH		; SYSTEM INTERCEPT - KEY CODE FUNCTION
   578                              <1> 	;STC				; SET CY=1 (IN CASE OF IRET)
   579                              <1> 	;INT	15H			; CASETTE CALL (AL)=KEY SCAN CODE
   580                              <1> 	;				; RETURNS CY=1 FOR INVALID FUNCTION
   581                              <1> 	;JC	KB_INT_02		; CONTINUE IF CARRY FLAG SET ((AL)=CODE)
   582                              <1> 	;JMP	K26			; EXIT IF SYSTEM HANDLES SCAN CODE
   583                              <1> 	;				; EXT HANDLES HARDWARE EOI AND ENABLE		
   584                              <1> 	;
   585                              <1> 	;-----	CHECK FOR A RESEND COMMAND TO KEYBOARD
   586                              <1> KB_INT_02:				; 	  (AL)= SCAN CODE
   587 0000106A FB                  <1> 	sti				; ENABLE INTERRUPTS AGAIN
   588 0000106B 3CFE                <1> 	cmp	al, KB_RESEND		; IS THE INPUT A RESEND
   589 0000106D 7411                <1>         je      short KB_INT_4          ; GO IF RESEND
   590                              <1> 	;
   591                              <1> 	;-----	CHECK FOR RESPONSE TO A COMMAND TO KEYBOARD
   592 0000106F 3CFA                <1> 	cmp	al, KB_ACK		; IS THE INPUT AN ACKNOWLEDGE
   593 00001071 751A                <1>         jne     short KB_INT_2          ; GO IF NOT
   594                              <1> 	;
   595                              <1> 	;-----	A COMMAND TO THE KEYBOARD WAS ISSUED
   596 00001073 FA                  <1> 	cli				; DISABLE INTERRUPTS
   597 00001074 800D[47660000]10    <1> 	or	byte [KB_FLAG_2], KB_FA ; INDICATE ACK RECEIVED
   598 0000107B E97A020000          <1>         jmp     K26                     ; RETURN IF NOT (ACK RETURNED FOR DATA)
   599                              <1> 	;
   600                              <1> 	;-----	RESEND THE LAST BYTE
   601                              <1> KB_INT_4:
   602 00001080 FA                  <1> 	cli				; DISABLE INTERRUPTS
   603 00001081 800D[47660000]20    <1> 	or	byte [KB_FLAG_2], KB_FE ; INDICATE RESEND RECEIVED
   604 00001088 E96D020000          <1>         jmp     K26                     ; RETURN IF NOT ACK RETURNED FOR DATA)
   605                              <1> 	;
   606                              <1> ;-----	UPDATE MODE INDICATORS IF CHANGE IN STATE
   607                              <1> KB_INT_2:
   608 0000108D 6650                <1> 	push 	ax			; SAVE DATA IN
   609 0000108F E83D060000          <1> 	call	MAKE_LED		; GO GET MODE INDICATOR DATA BYTE
   610 00001094 8A1D[47660000]      <1> 	mov	bl, [KB_FLAG_2] 	; GET PREVIOUS BITS
   611 0000109A 30C3                <1> 	xor	bl, al			; SEE IF ANY DIFFERENT
   612 0000109C 80E307              <1> 	and	bl, KB_LEDS		; ISOLATE INDICATOR BITS
   613 0000109F 7405                <1> 	jz	short UP0		; IF NO CHANGE BYPASS UPDATE
   614 000010A1 E8C0050000          <1> 	call	SND_LED			; GO TURN ON MODE INDICATORS
   615                              <1> UP0:
   616 000010A6 6658                <1> 	pop	ax			; RESTORE DATA IN
   617                              <1> ;------------------------------------------------------------------------
   618                              <1> ;	START OF KEY PROCESSING						;
   619                              <1> ;------------------------------------------------------------------------
   620 000010A8 88C4                <1> 	mov	ah, al			; SAVE SCAN CODE IN AH ALSO
   621                              <1> 	;
   622                              <1> 	;-----	TEST FOR OVERRUN SCAN CODE FROM KEYBOARD
   623 000010AA 3CFF                <1> 	cmp	al, KB_OVER_RUN		; IS THIS AN OVERRUN CHAR
   624 000010AC 0F843F050000        <1>         je      K62			; BUFFER_FULL_BEEP
   625                              <1> 	;
   626                              <1> K16:	
   627 000010B2 8A3D[48660000]      <1> 	mov	bh, [KB_FLAG_3]		; LOAD FLAGS FOR TESTING
   628                              <1> 	;
   629                              <1> 	;-----	TEST TO SEE IF A READ_ID IS IN PROGRESS
   630 000010B8 F6C7C0              <1> 	test 	bh, RD_ID+LC_AB 	; ARE WE DOING A READ ID?
   631 000010BB 7449                <1> 	jz	short NOT_ID		; CONTINUE IF NOT
   632 000010BD 7917                <1> 	jns	short TST_ID_2		; IS THE RD_ID FLAG ON?
   633 000010BF 3CAB                <1> 	cmp	al, ID_1		; IS THIS THE 1ST ID CHARACTER?
   634 000010C1 7507                <1> 	jne	short RST_RD_ID
   635 000010C3 800D[48660000]40    <1> 	or	byte [KB_FLAG_3], LC_AB ; INDICATE 1ST ID WAS OK
   636                              <1> RST_RD_ID:
   637 000010CA 8025[48660000]7F    <1> 	and	byte [KB_FLAG_3], ~RD_ID ; RESET THE READ ID FLAG
   638                              <1>         ;jmp    short ID_EX		; AND EXIT
   639 000010D1 E924020000          <1> 	jmp	K26
   640                              <1> 	;
   641                              <1> TST_ID_2:
   642 000010D6 8025[48660000]BF    <1> 	and	byte [KB_FLAG_3], ~LC_AB ; RESET FLAG
   643 000010DD 3C54                <1> 	cmp	al, ID_2A		; IS THIS THE 2ND ID CHARACTER?
   644 000010DF 7419                <1>         je	short KX_BIT		; JUMP IF SO
   645 000010E1 3C41                <1> 	cmp	al, ID_2		; IS THIS THE 2ND ID CHARACTER?
   646                              <1>         ;jne	short ID_EX		; LEAVE IF NOT
   647 000010E3 0F8511020000        <1> 	jne	K26
   648                              <1> 	;
   649                              <1> 	;-----	A READ ID SAID THAT IT WAS ENHANCED KEYBOARD
   650 000010E9 F6C720              <1> 	test	bh, SET_NUM_LK 		; SHOULD WE SET NUM LOCK?
   651 000010EC 740C                <1>         jz      short KX_BIT		; EXIT IF NOT
   652 000010EE 800D[45660000]20    <1> 	or	byte [KB_FLAG], NUM_STATE ; FORCE NUM LOCK ON
   653 000010F5 E86C050000          <1> 	call	SND_LED			; GO SET THE NUM LOCK INDICATOR
   654                              <1> KX_BIT:
   655 000010FA 800D[48660000]10    <1> 	or	byte [KB_FLAG_3], KBX	; INDICATE ENHANCED KEYBOARD WAS FOUND
   656 00001101 E9F4010000          <1> ID_EX:	jmp     K26			; EXIT
   657                              <1> 	;
   658                              <1> NOT_ID:
   659 00001106 3CE0                <1> 	cmp	al, MC_E0		; IS THIS THE GENERAL MARKER CODE?
   660 00001108 750C                <1> 	jne	short TEST_E1
   661 0000110A 800D[48660000]12    <1> 	or	byte [KB_FLAG_3], LC_E0+KBX ; SET FLAG BIT, SET KBX, AND
   662                              <1> 	;jmp	short EXIT		; THROW AWAY THIS CODE
   663 00001111 E9EB010000          <1> 	jmp	K26A	
   664                              <1> TEST_E1:	
   665 00001116 3CE1                <1> 	cmp	al, MC_E1		; IS THIS THE PAUSE KEY?
   666 00001118 750C                <1> 	jne	short NOT_HC
   667 0000111A 800D[48660000]11    <1> 	or	byte [KB_FLAG_3], LC_E1+KBX ; SET FLAG BIT, SET KBX, AND
   668 00001121 E9DB010000          <1> EXIT:	jmp	K26A			; THROW AWAY THIS CODE
   669                              <1> 	;
   670                              <1> NOT_HC:
   671 00001126 247F                <1> 	and	al, 07Fh		; TURN OFF THE BREAK BIT
   672 00001128 F6C702              <1> 	test	bh, LC_E0		; LAST CODE THE E0 MARKER CODE
   673 0000112B 7414                <1> 	jz	short NOT_LC_E0		; JUMP IF NOT
   674                              <1> 	;
   675 0000112D BF[32650000]        <1> 	mov	edi, _K6+6		; IS THIS A SHIFT KEY?
   676 00001132 AE                  <1> 	scasb
   677 00001133 0F84C1010000        <1>         je      K26 ; K16B              ; YES, THROW AWAY & RESET FLAG
   678 00001139 AE                  <1> 	scasb
   679 0000113A 757C                <1> 	jne	short K16A		; NO, CONTINUE KEY PROCESSING
   680                              <1> 	;jmp	short K16B		; YES, THROW AWAY & RESET FLAG
   681 0000113C E9B9010000          <1> 	jmp	K26
   682                              <1> 	;
   683                              <1> NOT_LC_E0:
   684 00001141 F6C701              <1> 	test	bh, LC_E1		; LAST CODE THE E1 MARKER CODE?
   685 00001144 7435                <1> 	jz	short T_SYS_KEY		; JUMP IF NOT
   686 00001146 B904000000          <1> 	mov	ecx, 4			; LENGHT OF SEARCH
   687 0000114B BF[30650000]        <1> 	mov	edi, _K6+4		; IS THIS AN ALT, CTL, OR SHIFT?
   688 00001150 F2AE                <1> 	repne	scasb			; CHECK IT
   689                              <1> 	;je	short EXIT		; THROW AWAY IF SO
   690 00001152 0F84A9010000        <1> 	je	K26A			
   691                              <1> 	;
   692 00001158 3C45                <1> 	cmp	al, NUM_KEY		; IS IT THE PAUSE KEY?
   693                              <1> 	;jne	short K16B		; NO, THROW AWAY & RESET FLAG
   694 0000115A 0F859A010000        <1> 	jne	K26
   695 00001160 F6C480              <1> 	test	ah, 80h			; YES, IS IT THE BREAK OF THE KEY?
   696                              <1> 	;jnz	short K16B		; YES, THROW THIS AWAY, TOO	
   697 00001163 0F8591010000        <1> 	jnz	K26
   698                              <1>         ; 20/02/2015 
   699 00001169 F605[46660000]08    <1> 	test	byte [KB_FLAG_1],HOLD_STATE ;  NO, ARE WE PAUSED ALREADY?
   700                              <1> 	;jnz	short K16B		;  YES, THROW AWAY
   701 00001170 0F8584010000        <1> 	jnz	K26
   702 00001176 E9E1020000          <1> 	jmp     K39P                    ; NO, THIS IS THE REAL PAUSE STATE
   703                              <1> 	;
   704                              <1> 	;-----	TEST FOR SYSTEM KEY
   705                              <1> T_SYS_KEY:
   706 0000117B 3C54                <1> 	cmp	al, SYS_KEY		; IS IT THE SYSTEM KEY?
   707 0000117D 7539                <1> 	jnz	short K16A		; CONTINUE IF NOT
   708                              <1> 	;
   709 0000117F F6C480              <1> 	test	ah, 80h			; CHECK IF THIS A BREAK CODE
   710 00001182 7524                <1> 	jnz	short K16C		; DO NOT TOUCH SYSTEM INDICATOR IF TRUE
   711                              <1> 	;
   712 00001184 F605[46660000]04    <1> 	test	byte [KB_FLAG_1], SYS_SHIFT ; SEE IF IN SYSTEM KEY HELD DOWN 
   713                              <1>         ;jnz	short K16B		; IF YES, DO NOT PROCESS SYSTEM INDICATOR	
   714 0000118B 0F8569010000        <1> 	jnz     K26			
   715                              <1> 	;
   716 00001191 800D[46660000]04    <1> 	or	byte [KB_FLAG_1], SYS_SHIFT ; INDICATE SYSTEM KEY DEPRESSED
   717 00001198 B020                <1> 	mov	al, EOI			; END OF INTERRUPT COMMAND
   718 0000119A E620                <1> 	out	20h, al ;out INTA00, al	; SEND COMMAND TO INTERRUPT CONTROL PORT
   719                              <1> 					; INTERRUPT-RETURN-NO-EOI
   720 0000119C B0AE                <1> 	mov	al, ENA_KBD		; INSURE KEYBOARD IS ENABLED
   721 0000119E E862040000          <1> 	call	SHIP_IT			; EXECUTE ENABLE
   722                              <1> 	; !!! SYSREQ !!! function/system call (INTERRUPT) must be here !!!
   723                              <1> 	;MOV	AL, 8500H		; FUNCTION VALUE FOR MAKE OF SYSTEM KEY
   724                              <1> 	;STI				; MAKE SURE INTERRUPTS ENABLED
   725                              <1> 	;INT	15H			; USER INTERRUPT	
   726 000011A3 E965010000          <1>         jmp     K27A                    ; END PROCESSING
   727                              <1> 	;
   728                              <1> ;K16B:	jmp	K26			; IGNORE SYSTEM KEY
   729                              <1> 	;
   730                              <1> K16C:
   731 000011A8 8025[46660000]FB    <1> 	and	byte [KB_FLAG_1], ~SYS_SHIFT ; TURN OFF SHIFT KEY HELD DOWN
   732 000011AF B020                <1> 	mov	al, EOI			; END OF INTERRUPT COMMAND
   733 000011B1 E620                <1> 	out	20h, al ;out INTA00, al ; SEND COMMAND TO INTERRUPT CONTROL PORT
   734                              <1> 					; INTERRUPT-RETURN-NO-EOI
   735                              <1> 	;MOV	AL, ENA_KBD		; INSURE KEYBOARD IS ENABLED
   736                              <1> 	;CALL	SHIP_IT			; EXECUTE ENABLE
   737                              <1> 	;
   738                              <1> 	;MOV	AX, 8501H		; FUNCTION VALUE FOR BREAK OF SYSTEM KEY
   739                              <1> 	;STI				; MAKE SURE INTERRUPTS ENABLED
   740                              <1> 	;INT	15H			; USER INTERRUPT
   741                              <1> 	;JMP	K27A			; INGONRE SYSTEM KEY				
   742                              <1> 	;
   743 000011B3 E94E010000          <1> 	jmp     K27			; IGNORE SYSTEM KEY
   744                              <1> 	;
   745                              <1> 	;-----	TEST FOR SHIFT KEYS
   746                              <1> K16A:
   747 000011B8 8A1D[45660000]      <1> 	mov	bl, [KB_FLAG]		; PUT STATE FLAGS IN BL
   748 000011BE BF[2C650000]        <1> 	mov	edi, _K6		; SHIFT KEY TABLE offset
   749 000011C3 B908000000          <1> 	mov	ecx, _K6L		; LENGTH
   750 000011C8 F2AE                <1> 	repne	scasb			; LOOK THROUGH THE TABLE FOR A MATCH
   751 000011CA 88E0                <1> 	mov	al, ah			; RECOVER SCAN CODE
   752 000011CC 0F8510010000        <1>         jne     K25                     ; IF NO MATCH, THEN SHIFT NOT FOUND
   753                              <1> 	;
   754                              <1> 	;------	SHIFT KEY FOUND
   755                              <1> K17:
   756 000011D2 81EF[2D650000]      <1>         sub     edi, _K6+1              ; ADJUST PTR TO SCAN CODE MATCH
   757 000011D8 8AA7[34650000]      <1>        	mov     ah, [edi+_K7]       	; GET MASK INTO AH
   758 000011DE B102                <1> 	mov	cl, 2			; SETUP COUNT FOR FLAG SHIFTS
   759 000011E0 A880                <1> 	test	al, 80h			; TEST FOR BREAK KEY
   760 000011E2 0F8596000000        <1>         jnz     K23                     ; JUMP OF BREAK
   761                              <1> 	;
   762                              <1> 	;-----	SHIFT MAKE FOUND, DETERMINE SET OR TOGGLE
   763                              <1> K17C:
   764 000011E8 80FC10              <1> 	cmp	ah, SCROLL_SHIFT
   765 000011EB 732B                <1> 	jae	short K18		; IF SCROLL SHIFT OR ABOVE, TOGGLE KEY
   766                              <1> 	;
   767                              <1> 	;-----	PLAIN SHIFT KEY, SET SHIFT ON
   768 000011ED 0825[45660000]      <1> 	or	[KB_FLAG], ah		; TURN ON SHIFT BIT
   769 000011F3 A80C                <1>         test	al, CTL_SHIFT+ALT_SHIFT ; IS IT ALT OR CTRL?
   770                              <1> 	;jnz	short K17D		; YES, MORE FLAGS TO SET
   771 000011F5 0F84FF000000        <1> 	jz	K26			; NO, INTERRUPT RETURN
   772                              <1> K17D:
   773 000011FB F6C702              <1> 	test	bh, LC_E0		; IS THIS ONE OF NEW KEYS?
   774 000011FE 740B                <1> 	jz 	short K17E		; NO, JUMP
   775 00001200 0825[48660000]      <1> 	or	[KB_FLAG_3], ah		; SET BITS FOR RIGHT CTRL, ALT
   776 00001206 E9EF000000          <1> 	jmp	K26			; INTERRUPT RETURN
   777                              <1> K17E:
   778 0000120B D2EC                <1> 	shr	ah, cl			; MOVE FLAG BITS TWO POSITIONS
   779 0000120D 0825[46660000]      <1> 	or	[KB_FLAG_1], ah		; SET BITS FOR LEFT CTRL, ALT
   780 00001213 E9E2000000          <1> 	jmp	K26
   781                              <1> 	;
   782                              <1> 	;-----	TOGGLED SHIFT KEY, TEST FOR 1ST MAKE OR NOT
   783                              <1> K18:					; SHIFT-TOGGLE
   784 00001218 F6C304              <1> 	test	bl, CTL_SHIFT 		; CHECK CTL SHIFT STATE
   785                              <1>         ;jz    	short K18A              ; JUMP IF NOT CTL STATE
   786 0000121B 0F85C1000000        <1>         jnz     K25                     ; JUMP IF CTL STATE
   787                              <1> K18A:
   788 00001221 3C52                <1> 	cmp	al, INS_KEY		; CHECK FOR INSERT KEY
   789 00001223 7524                <1> 	jne	short K22		; JUMP IF NOT INSERT KEY
   790 00001225 F6C308              <1> 	test	bl, ALT_SHIFT 		; CHECK FOR ALTERNATE SHIFT
   791                              <1>       	;jz	short K18B		; JUMP IF NOT ALTERNATE SHIFT	
   792 00001228 0F85B4000000        <1>         jnz     K25                     ; JUMP IF ALTERNATE SHIFT
   793                              <1> K18B:
   794 0000122E F6C702              <1> 	test	bh, LC_E0 ;20/02/2015	; IS THIS NEW INSERT KEY?
   795 00001231 7516                <1> 	jnz	short K22		; YES, THIS ONE'S NEVER A '0'
   796                              <1> K19:	
   797 00001233 F6C320              <1> 	test	bl, NUM_STATE 		; CHECK FOR BASE STATE
   798 00001236 750C                <1> 	jnz	short K21		; JUMP IF NUM LOCK IS ON
   799 00001238 F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; TEST FOR SHIFT STATE
   800 0000123B 740C                <1> 	jz	short K22		; JUMP IF BASE STATE
   801                              <1> K20:					; NUMERIC ZERO, NOT INSERT KEY
   802 0000123D 88C4                <1> 	mov	ah, al			; PUT SCAN CODE BACK IN AH
   803 0000123F E99E000000          <1>         jmp     K25                     ; NUMERAL '0', STNDRD. PROCESSING
   804                              <1> K21:					; MIGHT BE NUMERIC
   805 00001244 F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT
   806 00001247 74F4                <1> 	jz	short K20		; IS NUMERIC, STD. PROC.
   807                              <1> 	;
   808                              <1> K22:					; SHIFT TOGGLE KEY HIT; PROCESS IT
   809 00001249 8425[46660000]      <1> 	test	ah, [KB_FLAG_1] 	; IS KEY ALREADY DEPRESSED
   810 0000124F 0F85A5000000        <1>         jnz     K26                     ; JUMP IF KEY ALREADY DEPRESSED
   811                              <1> K22A:
   812 00001255 0825[46660000]      <1>         or      [KB_FLAG_1], ah 	; INDICATE THAT THE KEY IS DEPRESSED
   813 0000125B 3025[45660000]      <1> 	xor	[KB_FLAG], ah		; TOGGLE THE SHIFT STATE
   814                              <1> 	;
   815                              <1> 	;-----	TOGGLE LED IF CAPS, NUM  OR SCROLL KEY DEPRESSED
   816 00001261 F6C470              <1> 	test	ah, CAPS_SHIFT+NUM_SHIFT+SCROLL_SHIFT ; SHIFT TOGGLE?
   817 00001264 7409                <1> 	jz	short K22B		; GO IF NOT
   818                              <1> 	;
   819 00001266 6650                <1> 	push	ax			; SAVE SCAN CODE AND SHIFT MASK
   820 00001268 E8F9030000          <1> 	call	SND_LED			; GO TURN MODE INDICATORS ON
   821 0000126D 6658                <1> 	pop	ax			; RESTORE SCAN CODE
   822                              <1> K22B:
   823 0000126F 3C52                <1> 	cmp	al, INS_KEY		; TEST FOR 1ST MAKE OF INSERT KEY
   824 00001271 0F8583000000        <1>         jne     K26                     ; JUMP IF NOT INSERT KEY
   825 00001277 88C4                <1> 	mov	ah, al		        ; SCAN CODE IN BOTH HALVES OF AX
   826 00001279 E999000000          <1>         jmp     K28                     ; FLAGS UPDATED, PROC. FOR BUFFER
   827                              <1> 	;
   828                              <1> 	;-----	BREAK SHIFT FOUND
   829                              <1> K23:					; BREAK-SHIFT-FOUND
   830 0000127E 80FC10              <1> 	cmp	ah, SCROLL_SHIFT	; IS THIS A TOGGLE KEY
   831 00001281 F6D4                <1> 	not	ah			; INVERT MASK
   832 00001283 7355                <1> 	jae	short K24		; YES, HANDLE BREAK TOGGLE
   833 00001285 2025[45660000]      <1> 	and	[KB_FLAG], ah		; TURN OFF SHIFT BIT
   834 0000128B 80FCFB              <1> 	cmp	ah, ~CTL_SHIFT		; IS THIS ALT OR CTL?
   835 0000128E 7730                <1> 	ja	short K23D		; NO, ALL DONE
   836                              <1> 	;
   837 00001290 F6C702              <1> 	test	bh, LC_E0		; 2ND ALT OR CTL?
   838 00001293 7408                <1> 	jz	short K23A		; NO, HANSLE NORMALLY
   839 00001295 2025[48660000]      <1> 	and 	[KB_FLAG_3], ah		; RESET BIT FOR RIGHT ALT OR CTL
   840 0000129B EB08                <1> 	jmp	short K23B		; CONTINUE
   841                              <1> K23A:
   842 0000129D D2FC                <1> 	sar	ah, cl			; MOVE THE MASK BIT TWO POSITIONS
   843 0000129F 2025[46660000]      <1> 	and	[KB_FLAG_1], ah		; RESET BIT FOR LEFT ALT AND CTL
   844                              <1> K23B:
   845 000012A5 88C4                <1> 	mov	ah, al			; SAVE SCAN CODE
   846 000012A7 A0[48660000]        <1> 	mov	al, [KB_FLAG_3]		; GET RIGHT ALT & CTRL FLAGS
   847 000012AC D2E8                <1> 	shr	al, cl			; MOVE TO BITS 1 & 0
   848 000012AE 0A05[46660000]      <1> 	or	al, [KB_FLAG_1]		; PUT IN LEFT ALT & CTL FLAGS
   849 000012B4 D2E0                <1> 	shl	al, cl			; MOVE BACK TO BITS 3 & 2
   850 000012B6 240C                <1> 	and	al, ALT_SHIFT+CTL_SHIFT ; FILTER OUT OTHER GARBAGE
   851 000012B8 0805[45660000]      <1> 	or	[KB_FLAG], al		; PUT RESULT IN THE REAL FLAGS	
   852 000012BE 88E0                <1> 	mov	al, ah
   853                              <1> K23D:
   854 000012C0 3CB8                <1> 	cmp	al, ALT_KEY+80h		; IS THIS ALTERNATE SHIFT RELEASE
   855 000012C2 7536                <1> 	jne	short K26		; INTERRUPT RETURN
   856                              <1> 	;	
   857                              <1> 	;-----	ALTERNATE SHIFT KEY RELEASED, GET THE VALUE INTO BUFFER
   858 000012C4 A0[49660000]        <1> 	mov	al, [ALT_INPUT]
   859 000012C9 B400                <1> 	mov	ah, 0			; SCAN CODE OF 0
   860 000012CB 8825[49660000]      <1> 	mov	[ALT_INPUT], ah 	; ZERO OUT THE FIELD
   861 000012D1 3C00                <1> 	cmp	al, 0			; WAS THE INPUT = 0?
   862 000012D3 7425                <1> 	je	short K26		; INTERRUPT_RETURN
   863                              <1>         ; 29/01/2016
   864                              <1> 	;jmp     K61                    ; IT WASN'T, SO PUT IN BUFFER
   865 000012D5 E9D0020000          <1> 	jmp	_K60
   866                              <1> 	;
   867                              <1> K24:					; BREAK-TOGGLE
   868 000012DA 2025[46660000]      <1> 	and	[KB_FLAG_1], ah 	; INDICATE NO LONGER DEPRESSED
   869 000012E0 EB18                <1> 	jmp	short K26		; INTERRUPT_RETURN
   870                              <1> 	;
   871                              <1> 	;-----	TEST FOR HOLD STATE
   872                              <1> 					; AL, AH = SCAN CODE
   873                              <1> K25:					; NO-SHIFT-FOUND
   874 000012E2 3C80                <1> 	cmp	al, 80h			; TEST FOR BREAK KEY
   875 000012E4 7314                <1> 	jae	short K26		; NOTHING FOR BREAK CHARS FROM HERE ON
   876 000012E6 F605[46660000]08    <1> 	test	byte [KB_FLAG_1], HOLD_STATE ; ARE WE IN HOLD STATE
   877 000012ED 7428                <1> 	jz	short K28		; BRANCH AROUND TEST IF NOT
   878 000012EF 3C45                <1> 	cmp	al, NUM_KEY
   879 000012F1 7407                <1> 	je	short K26		; CAN'T END HOLD ON NUM_LOCK
   880 000012F3 8025[46660000]F7    <1> 	and	byte [KB_FLAG_1], ~HOLD_STATE ; TURN OFF THE HOLD STATE BIT
   881                              <1> 	;
   882                              <1> K26:
   883 000012FA 8025[48660000]FC    <1> 	and	byte [KB_FLAG_3], ~(LC_E0+LC_E1) ; RESET LAST CHAR H.C. FLAG
   884                              <1> K26A:					; INTERRUPT-RETURN
   885 00001301 FA                  <1> 	cli				; TURN OFF INTERRUPTS
   886 00001302 B020                <1> 	mov	al, EOI			; END OF INTERRUPT COMMAND
   887 00001304 E620                <1> 	out	20h, al	;out INTA00, al	; SEND COMMAND TO INTERRUPT CONTROL PORT
   888                              <1> K27:					; INTERRUPT-RETURN-NO-EOI
   889 00001306 B0AE                <1> 	mov	al, ENA_KBD		; INSURE KEYBOARD IS ENABLED
   890 00001308 E8F8020000          <1> 	call	SHIP_IT			; EXECUTE ENABLE
   891                              <1> K27A:
   892 0000130D FA                  <1> 	cli				; DISABLE INTERRUPTS
   893                              <1> 	;;mov	byte [intflg], 0 ; 07/01/2017 ;; 15/01/2017
   894 0000130E 07                  <1> 	pop	es			; RESTORE REGISTERS
   895 0000130F 1F                  <1> 	pop	ds
   896 00001310 5F                  <1> 	pop	edi
   897 00001311 5E                  <1> 	pop	esi
   898 00001312 5A                  <1> 	pop	edx
   899 00001313 59                  <1> 	pop	ecx
   900 00001314 5B                  <1> 	pop	ebx
   901 00001315 58                  <1> 	pop	eax
   902                              <1> 	;pop	ebp
   903 00001316 CF                  <1> 	iretd				; RETURN
   904                              <1> 
   905                              <1> 	;-----	NOT IN	HOLD STATE
   906                              <1> K28:					; NO-HOLD-STATE
   907 00001317 3C58                <1> 	cmp	al, 88			; TEST FOR OUT-OF-RANGE SCAN CODES
   908 00001319 77DF                <1> 	ja	short K26		; IGNORE IF OUT-OF-RANGE	
   909                              <1> 	;
   910 0000131B F6C308              <1> 	test	bl, ALT_SHIFT 		; ARE WE IN ALTERNATE SHIFT
   911                              <1>         ;jz	short K28A		; IF NOT ALTERNATE
   912 0000131E 0F84F1000000        <1>         jz      K38
   913                              <1> 	;
   914 00001324 F6C710              <1> 	test	bh, KBX			; IS THIS THE ENCHANCED KEYBOARD?
   915 00001327 740D                <1> 	jz	short K29		; NO, ALT STATE IS REAL
   916                              <1> 	 ;28/02/2015
   917 00001329 F605[46660000]04    <1> 	test	byte [KB_FLAG_1], SYS_SHIFT ; YES, IS SYSREQ KEY DOWN?
   918                              <1> 	;jz	short K29		;  NO, ALT STATE IS REAL
   919 00001330 0F85DF000000        <1> 	jnz	K38			; YES, THIS IS PHONY ALT STATE 
   920                              <1>         ;				; DUE TO PRESSING SYSREQ	
   921                              <1> ;K28A:	jmp	short K38
   922                              <1> 	;
   923                              <1> 	;-----	TEST FOR RESET KEY SEQUENCE (CTL ALT DEL)
   924                              <1> K29:					; TEST-RESET
   925 00001336 F6C304              <1> 	test	bl, CTL_SHIFT 		; ARE WE IN CONTROL SHIFT ALSO?
   926 00001339 740B                <1> 	jz	short K31		; NO_RESET
   927 0000133B 3C53                <1> 	cmp	al, DEL_KEY		; CTL-ALT STATE, TEST FOR DELETE KEY
   928 0000133D 7507                <1> 	jne	short K31		; NO_RESET, IGNORE
   929                              <1> 	;
   930                              <1> 	;-----	CTL-ALT-DEL HAS BEEN FOUND
   931                              <1>  	; 26/08/2014
   932                              <1> cpu_reset:
   933                              <1> 	; IBM PC/AT ROM BIOS source code - 10/06/85 (TEST4.ASM - PROC_SHUTDOWN)
   934                              <1> 	; Send FEh (system reset command) to the keyboard controller.
   935 0000133F B0FE                <1> 	mov	al, SHUT_CMD		; SHUTDOWN COMMAND
   936 00001341 E664                <1> 	out	STATUS_PORT, al		; SEND TO KEYBOARD CONTROL PORT
   937                              <1> khere:
   938 00001343 F4                  <1> 	hlt				; WAIT FOR 80286 RESET
   939 00001344 EBFD                <1> 	jmp 	short khere		; INSURE HALT
   940                              <1> 
   941                              <1> 	;
   942                              <1> 	;-----	IN ALTERNATE SHIFT, RESET NOT FOUND
   943                              <1> K31:					; NO-RESET
   944 00001346 3C39                <1> 	cmp	al, 57			; TEST FOR SPACE KEY
   945 00001348 7507                <1> 	jne	short K311		; NOT THERE
   946 0000134A B020                <1> 	mov	al, ' '			; SET SPACE CHAR
   947 0000134C E948020000          <1>         jmp     K57                     ; BUFFER_FILL
   948                              <1> K311:
   949 00001351 3C0F                <1> 	cmp	al, 15			; TEST FOR TAB KEY
   950 00001353 7509                <1> 	jne	short K312		; NOT THERE
   951 00001355 66B800A5            <1> 	mov	ax, 0A500h		; SET SPECIAL CODE FOR ALT-TAB
   952 00001359 E93B020000          <1>         jmp     K57                     ; BUFFER_FILL
   953                              <1> K312:
   954 0000135E 3C4A                <1> 	cmp	al, 74			; TEST FOR KEY PAD -
   955 00001360 0F84A2000000        <1>         je      K37B                    ; GO PROCESS
   956 00001366 3C4E                <1> 	cmp	al, 78			; TEST FOR KEY PAD +
   957 00001368 0F849A000000        <1>         je      K37B                    ; GO PROCESS
   958                              <1> 	;
   959                              <1> 	;-----	LOOK FOR KEY PAD ENTRY
   960                              <1> K32:					; ALT-KEY-PAD
   961 0000136E BF[08650000]        <1> 	mov	edi, K30		; ALT-INPUT-TABLE offset
   962 00001373 B90A000000          <1> 	mov	ecx, 10			; LOOK FOR ENTRY USING KEYPAD
   963 00001378 F2AE                <1> 	repne	scasb			; LOOK FOR MATCH
   964 0000137A 7525                <1> 	jne	short K33		; NO_ALT_KEYPAD
   965 0000137C F6C702              <1> 	test	bh, LC_E0		; IS THIS ONE OF THE NEW KEYS?
   966 0000137F 0F858A000000        <1>         jnz     K37C                    ; YES, JUMP, NOT NUMPAD KEY
   967 00001385 81EF[09650000]      <1> 	sub	edi, K30+1		; DI NOW HAS ENTRY VALUE
   968 0000138B A0[49660000]        <1> 	mov	al, [ALT_INPUT] 	; GET THE CURRENT BYTE
   969 00001390 B40A                <1> 	mov	ah, 10			; MULTIPLY BY 10
   970 00001392 F6E4                <1> 	mul	ah
   971 00001394 6601F8              <1> 	add	ax, di			; ADD IN THE LATEST ENTRY
   972 00001397 A2[49660000]        <1> 	mov	[ALT_INPUT], al 	; STORE IT AWAY
   973                              <1> ;K32A:
   974 0000139C E959FFFFFF          <1>         jmp     K26                     ; THROW AWAY THAT KEYSTROKE
   975                              <1> 	;
   976                              <1> 	;-----	LOOK FOR SUPERSHIFT ENTRY
   977                              <1> K33:					; NO-ALT-KEYPAD
   978 000013A1 C605[49660000]00    <1>         mov     byte [ALT_INPUT], 0     ; ZERO ANY PREVIOUS ENTRY INTO INPUT
   979 000013A8 B91A000000          <1> 	mov	ecx, 26			; (DI),(ES) ALREADY POINTING
   980 000013AD F2AE                <1> 	repne	scasb			; LOOK FOR MATCH IN ALPHABET
   981 000013AF 7450                <1> 	je	short K37A		; MATCH FOUND, GO FILLL THE BUFFER
   982                              <1> 	;
   983                              <1> 	;-----	LOOK FOR TOP ROW OF ALTERNATE SHIFT
   984                              <1> K34:					; ALT-TOP-ROW
   985 000013B1 3C02                <1> 	cmp	al, 2			; KEY WITH '1' ON IT
   986 000013B3 7253                <1> 	jb	short K37B		; MUST BE ESCAPE
   987 000013B5 3C0D                <1> 	cmp	al, 13			; IS IT IN THE REGION
   988 000013B7 7705                <1> 	ja	short K35		; NO, ALT SOMETHING ELSE
   989 000013B9 80C476              <1> 	add	ah, 118			; CONVERT PSEUDO SCAN CODE TO RANGE
   990 000013BC EB43                <1> 	jmp	short K37A		; GO FILL THE BUFFER
   991                              <1> 	;
   992                              <1> 	;-----	TRANSLATE ALTERNATE SHIFT PSEUDO SCAN CODES
   993                              <1> K35:					; ALT-FUNCTION
   994 000013BE 3C57                <1> 	cmp	al, F11_M		; IS IT F11?	
   995 000013C0 7209                <1> 	jb	short K35A ; 20/02/2015	; NO, BRANCH
   996 000013C2 3C58                <1> 	cmp	al, F12_M		; IS IT F12?
   997 000013C4 7705                <1> 	ja	short K35A ; 20/02/2015	; NO, BRANCH
   998 000013C6 80C434              <1> 	add	ah, 52			; CONVERT TO PSEUDO SCAN CODE
   999 000013C9 EB36                <1> 	jmp	short K37A		; GO FILL THE BUFFER
  1000                              <1> K35A:
  1001 000013CB F6C702              <1> 	test	bh, LC_E0		; DO WE HAVE ONE OF THE NEW KEYS?
  1002 000013CE 7422                <1> 	jz	short K37		; NO, JUMP
  1003 000013D0 3C1C                <1> 	cmp	al, 28			; TEST FOR KEYPAD ENTER
  1004 000013D2 7509                <1>         jne     short K35B              ; NOT THERE
  1005 000013D4 66B800A6            <1> 	mov	ax, 0A600h		; SPECIAL CODE
  1006 000013D8 E9BC010000          <1> 	jmp	K57			; BUFFER FILL
  1007                              <1> K35B:
  1008 000013DD 3C53                <1> 	cmp	al, 83			; TEST FOR DELETE KEY
  1009 000013DF 742E                <1> 	je	short K37C		; HANDLE WITH OTHER EDIT KEYS
  1010 000013E1 3C35                <1> 	cmp	al, 53			; TEST FOR KEYPAD /
  1011                              <1> 	;jne	short K32A		; NOT THERE, NO OTHER E0 SPECIALS	
  1012 000013E3 0F8511FFFFFF        <1>         jne     K26
  1013 000013E9 66B800A4            <1> 	mov	ax, 0A400h		; SPECIAL CODE
  1014 000013ED E9A7010000          <1> 	jmp	K57			; BUFFER FILL
  1015                              <1> K37:
  1016 000013F2 3C3B                <1> 	cmp	al, 59			; TEST FOR FUNCTION KEYS (F1)
  1017 000013F4 7212                <1>         jb      short K37B		; NO FN, HANDLE W/OTHER EXTENDED
  1018 000013F6 3C44                <1> 	cmp	al, 68			; IN KEYPAD REGION?
  1019                              <1>         ;ja	short K32A		; IF SO, IGNORE
  1020 000013F8 0F87FCFEFFFF        <1>         ja      K26
  1021 000013FE 80C42D              <1> 	add	ah, 45			; CONVERT TO PSEUDO SCAN CODE
  1022                              <1> K37A:
  1023 00001401 B000                <1> 	mov	al, 0			; ASCII CODE OF ZERO
  1024 00001403 E991010000          <1>         jmp     K57                     ; PUT IT IN THE BUFFER
  1025                              <1> K37B:
  1026 00001408 B0F0                <1> 	mov	al, 0F0h		; USE SPECIAL ASCII CODE
  1027 0000140A E98A010000          <1> 	jmp     K57                     ; PUT IT IN THE BUFFER
  1028                              <1> K37C:
  1029 0000140F 0450                <1> 	add	al, 80			; CONVERT SCAN CODE (EDIT KEYS)
  1030 00001411 88C4                <1> 	mov	ah, al			; (SCAN CODE NOT IN AH FOR INSERT)
  1031 00001413 EBEC                <1> 	jmp     short K37A              ; PUT IT IN THE BUFFER
  1032                              <1> 	;
  1033                              <1> 	;-----	NOT IN ALTERNATE SHIFT
  1034                              <1> K38:					; NOT-ALT-SHIFT
  1035                              <1> 					; BL STILL HAS SHIFT FLAGS
  1036 00001415 F6C304              <1> 	test	bl, CTL_SHIFT 		; ARE WE IN CONTROL SHIFT?
  1037                              <1> 	;jnz	short K38A		; YES, START PROCESSING	
  1038 00001418 0F84B0000000        <1>         jz      K44                     ; NOT-CTL-SHIFT
  1039                              <1> 	;
  1040                              <1> 	;-----	CONTROL SHIFT, TEST SPECIAL CHARACTERS
  1041                              <1> 	;-----	TEST FOR BREAK
  1042                              <1> K38A:
  1043 0000141E 3C46                <1> 	cmp	al, SCROLL_KEY		; TEST FOR BREAK
  1044 00001420 7531                <1> 	jne	short K39		; JUMP, NO-BREAK
  1045 00001422 F6C710              <1> 	test	bh, KBX			; IS THIS THE ENHANCED KEYBOARD?
  1046 00001425 7405                <1> 	jz	short K38B		; NO, BREAK IS VALID	
  1047 00001427 F6C702              <1> 	test	bh, LC_E0		; YES, WAS LAST CODE AN E0?
  1048 0000142A 7427                <1> 	jz	short K39		; NO-BREAK, TEST FOR PAUSE	
  1049                              <1> K38B:
  1050 0000142C 8B1D[52660000]      <1> 	mov	ebx, [BUFFER_HEAD] 	; RESET BUFFER TO EMPTY
  1051 00001432 891D[56660000]      <1> 	mov	[BUFFER_TAIL], ebx
  1052 00001438 C605[44660000]80    <1> 	mov	byte [BIOS_BREAK], 80h  ; TURN ON BIOS_BREAK BIT
  1053                              <1> 	;
  1054                              <1> 	;-----	ENABLE KEYBOARD
  1055 0000143F B0AE                <1> 	mov	al, ENA_KBD		; ENABLE KEYBOARD
  1056 00001441 E8BF010000          <1> 	call	SHIP_IT			; EXECUTE ENABLE
  1057                              <1> 	;
  1058                              <1> 	; CTRL+BREAK code here !!!
  1059                              <1> 	;INT	1BH			; BREAK INTERRUPT VECTOR
  1060                              <1> 	; 17/10/2015	
  1061 00001446 E833580000          <1> 	call	ctrlbrk ; control+break subroutine
  1062                              <1> 	;
  1063 0000144B 6629C0              <1> 	sub	ax, ax			; PUT OUT DUMMY CHARACTER
  1064 0000144E E946010000          <1>         jmp     K57                     ; BUFFER_FILL
  1065                              <1> 	;
  1066                              <1> 	;-----	TEST FOR PAUSE
  1067                              <1> K39:					; NO_BREAK
  1068 00001453 F6C710              <1> 	test	bh, KBX			; IS THIS THE ENHANCED KEYBOARD?
  1069 00001456 7537                <1> 	jnz	short K41		; YES, THEN THIS CAN'T BE PAUSE	
  1070 00001458 3C45                <1> 	cmp	al, NUM_KEY		; LOOK FOR PAUSE KEY
  1071 0000145A 7533                <1> 	jne	short K41		; NO-PAUSE
  1072                              <1> K39P:
  1073 0000145C 800D[46660000]08    <1> 	or	byte [KB_FLAG_1], HOLD_STATE ; TURN ON THE HOLD FLAG
  1074                              <1> 	;
  1075                              <1> 	;-----	ENABLE KEYBOARD
  1076 00001463 B0AE                <1> 	mov	al, ENA_KBD		; ENABLE KEYBOARD
  1077 00001465 E89B010000          <1> 	call	SHIP_IT			; EXECUTE ENABLE
  1078                              <1> K39A:
  1079 0000146A B020                <1> 	mov	al, EOI			; END OF INTERRUPT TO CONTROL PORT
  1080 0000146C E620                <1> 	out	20h, al ;out INTA00, al	; ALLOW FURTHER KEYSTROKE INTERRUPTS
  1081                              <1> 	;
  1082                              <1> 	;-----	DURING PAUSE INTERVAL, TURN COLOR CRT BACK ON
  1083 0000146E 803D[7A660000]07    <1>         cmp     byte [CRT_MODE], 7      ; IS THIS BLACK AND WHITE CARD
  1084 00001475 740A                <1>         je      short K40              	; YES, NOTHING TO DO
  1085 00001477 66BAD803            <1> 	mov	dx, 03D8h		; PORT FOR COLOR CARD
  1086 0000147B A0[7B660000]        <1>         mov     al, [CRT_MODE_SET] 	; GET THE VALUE OF THE CURRENT MODE
  1087 00001480 EE                  <1> 	out	dx, al			; SET THE CRT MODE, SO THAT CRT IS ON
  1088                              <1> 	;
  1089                              <1> K40:					; PAUSE-LOOP
  1090 00001481 F605[46660000]08    <1>         test    byte [KB_FLAG_1], HOLD_STATE ; CHECK HOLD STATE FLAG
  1091 00001488 75F7                <1> 	jnz	short K40		; LOOP UNTIL FLAG TURNED OFF
  1092                              <1> 	;
  1093 0000148A E977FEFFFF          <1>         jmp     K27                     ; INTERRUPT_RETURN_NO_EOI
  1094                              <1>         ;
  1095                              <1> 	;-----	TEST SPECIAL CASE KEY 55
  1096                              <1> K41:					; NO-PAUSE
  1097 0000148F 3C37                <1> 	cmp	al, 55			; TEST FOR */PRTSC KEY
  1098 00001491 7513                <1> 	jne	short K42		; NOT-KEY-55
  1099 00001493 F6C710              <1> 	test	bh, KBX			; IS THIS THE ENHANCED KEYBOARD?
  1100 00001496 7405                <1> 	jz	short K41A		; NO, CTL-PRTSC IS VALID	
  1101 00001498 F6C702              <1> 	test	bh, LC_E0		; YES, WAS LAST CODE AN E0?
  1102 0000149B 7421                <1> 	jz	short K42B		; NO, TRANSLATE TO A FUNCTION
  1103                              <1> K41A:	
  1104 0000149D 66B80072            <1> 	mov	ax, 114*256		; START/STOP PRINTING SWITCH
  1105 000014A1 E9F3000000          <1>         jmp     K57                     ; BUFFER_FILL
  1106                              <1> 	;
  1107                              <1> 	;-----	SET UP TO TRANSLATE CONTROL SHIFT
  1108                              <1> K42:					; NOT-KEY-55
  1109 000014A6 3C0F                <1> 	cmp	al, 15			; IS IT THE TAB KEY?
  1110 000014A8 7414                <1> 	je	short K42B		; YES, XLATE TO FUNCTION CODE
  1111 000014AA 3C35                <1> 	cmp	al, 53			; IS IT THE / KEY?
  1112 000014AC 750E                <1> 	jne	short K42A		; NO, NO MORE SPECIAL CASES	
  1113 000014AE F6C702              <1> 	test	bh, LC_E0		; YES, IS IT FROM THE KEY PAD?
  1114 000014B1 7409                <1> 	jz	short K42A		; NO, JUST TRANSLATE
  1115 000014B3 66B80095            <1> 	mov	ax, 9500h		; YES, SPECIAL CODE FOR THIS ONE
  1116 000014B7 E9DD000000          <1> 	jmp	K57			; BUFFER FILL	
  1117                              <1> K42A: 
  1118                              <1> 	;;mov	ebx, _K8		; SET UP TO TRANSLATE CTL
  1119 000014BC 3C3B                <1> 	cmp	al, 59			; IS IT IN CHARACTER TABLE?
  1120                              <1>         ;jb	short K45F              ; YES, GO TRANSLATE CHAR
  1121                              <1> 	;;jb	K56 ; 20/02/2015
  1122                              <1> 	;;jmp	K64 ; 20/02/2015
  1123                              <1> K42B:
  1124 000014BE BB[3C650000]        <1> 	mov	ebx, _K8		; SET UP TO TRANSLATE CTL
  1125 000014C3 0F82AE000000        <1> 	jb	K56 ;; 20/02/2015	
  1126 000014C9 E9B9000000          <1> 	jmp	K64	
  1127                              <1>         ;
  1128                              <1> 	;-----	NOT IN CONTROL SHIFT
  1129                              <1> K44:					; NOT-CTL-SHIFT
  1130 000014CE 3C37                <1> 	cmp	al, 55			; PRINT SCREEN KEY?
  1131 000014D0 7528                <1> 	jne	short K45		; NOT PRINT SCREEN
  1132 000014D2 F6C710              <1> 	test	bh, KBX			; IS THIS ENHANCED KEYBOARD?
  1133 000014D5 7407                <1> 	jz	short K44A		; NO, TEST FOR SHIFT STATE	
  1134 000014D7 F6C702              <1> 	test	bh, LC_E0		; YES, LAST CODE A MARKER?
  1135 000014DA 7507                <1> 	jnz	short K44B		; YES, IS PRINT SCREEN
  1136 000014DC EB41                <1> 	jmp	short K45C		; NO, TRANSLATE TO '*' CHARACTER
  1137                              <1> K44A:
  1138 000014DE F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; NOT 101 KBD, SHIFT KEY DOWN?
  1139 000014E1 743C                <1> 	jz	short K45C		; NO, TRANSLATE TO '*' CHARACTER
  1140                              <1> 	;
  1141                              <1> 	;-----	ISSUE INTERRUPT TO INDICATE PRINT SCREEN FUNCTION
  1142                              <1> K44B:
  1143 000014E3 B0AE                <1> 	mov	al, ENA_KBD		; INSURE KEYBOARD IS ENABLED
  1144 000014E5 E81B010000          <1> 	call	SHIP_IT			; EXECUTE ENABLE
  1145 000014EA B020                <1> 	mov	al, EOI			; END OF CURRENT INTERRUPT
  1146 000014EC E620                <1> 	out	20h, al ;out INTA00, al	; SO FURTHER THINGS CAN HAPPEN
  1147                              <1> 	; Print Screen !!!		; ISSUE PRINT SCREEN INTERRUPT (INT 05h)
  1148                              <1> 	;PUSH 	BP			; SAVE POINTER
  1149                              <1> 	;INT 	5H			; ISSUE PRINT SCREEN INTERRUPT
  1150                              <1> 	;POP	BP			; RESTORE POINTER
  1151 000014EE 8025[48660000]FC    <1>         and     byte [KB_FLAG_3], ~(LC_E0+LC_E1) ; ZERO OUT THESE FLAGS
  1152 000014F5 E90CFEFFFF          <1>         jmp     K27                     ; GO BACK WITHOUT EOI OCCURRING
  1153                              <1> 	;
  1154                              <1> 	;-----	HANDLE IN-CORE KEYS
  1155                              <1> K45:					; NOT-PRINT-SCREEN
  1156 000014FA 3C3A                <1> 	cmp	al, 58			; TEST FOR IN-CORE AREA
  1157 000014FC 7734                <1> 	ja	short K46		; JUMP IF NOT
  1158 000014FE 3C35                <1> 	cmp	al, 53			; IS THIS THE '/' KEY?
  1159 00001500 7505                <1> 	jne	short K45A		; NO, JUMP
  1160 00001502 F6C702              <1> 	test	bh, LC_E0		; WAS THE LAST CODE THE MARKER?
  1161 00001505 7518                <1> 	jnz	short K45C		; YES, TRANSLATE TO CHARACTER
  1162                              <1> K45A:
  1163 00001507 B91A000000          <1> 	mov	ecx, 26			; LENGHT OF SEARCH
  1164 0000150C BF[12650000]        <1> 	mov	edi, K30+10		; POINT TO TABLE OF A-Z CHARS
  1165 00001511 F2AE                <1> 	repne	scasb			; IS THIS A LETTER KEY?
  1166                              <1> 		; 20/02/2015
  1167 00001513 7505                <1> 	jne	short K45B              ; NO, SYMBOL KEY
  1168                              <1> 	;
  1169 00001515 F6C340              <1> 	test	bl, CAPS_STATE		; ARE WE IN CAPS_LOCK?
  1170 00001518 750C                <1> 	jnz	short K45D		; TEST FOR SURE
  1171                              <1> K45B:
  1172 0000151A F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; ARE WE IN SHIFT STATE?
  1173 0000151D 750C                <1> 	jnz	short K45E		; YES, UPPERCASE
  1174                              <1> 					; NO, LOWERCASE
  1175                              <1> K45C:
  1176 0000151F BB[94650000]        <1> 	mov	ebx, K10		; TRANSLATE TO LOWERCASE LETTERS
  1177 00001524 EB51                <1> 	jmp	short K56	
  1178                              <1> K45D:					; ALMOST-CAPS-STATE
  1179 00001526 F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; CL ON. IS SHIFT ON, TOO?
  1180 00001529 75F4                <1> 	jnz	short K45C		; SHIFTED TEMP OUT OF CAPS STATE
  1181                              <1> K45E:
  1182 0000152B BB[EC650000]        <1> 	mov	ebx, K11		; TRANSLATE TO UPPER CASE LETTERS
  1183 00001530 EB45                <1> K45F:	jmp	short K56
  1184                              <1> 	;
  1185                              <1> 	;-----	TEST FOR KEYS F1 - F10
  1186                              <1> K46:					; NOT IN-CORE AREA
  1187 00001532 3C44                <1> 	cmp	al, 68			; TEST FOR F1 - F10
  1188                              <1> 	;ja	short K47		; JUMP IF NOT
  1189                              <1> 	;jmp	short K53		; YES, GO DO FN KEY PROCESS			
  1190 00001534 7635                <1> 	jna	short K53		
  1191                              <1> 	;
  1192                              <1> 	;-----	HANDLE THE NUMERIC PAD KEYS
  1193                              <1> K47:					; NOT F1 - F10
  1194 00001536 3C53                <1> 	cmp	al, 83			; TEST NUMPAD KEYS
  1195 00001538 772D                <1> 	ja	short K52		; JUMP IF NOT
  1196                              <1> 	;
  1197                              <1> 	;-----	KEYPAD KEYS, MUST TEST NUM LOCK FOR DETERMINATION
  1198                              <1> K48:
  1199 0000153A 3C4A                <1> 	cmp	al , 74			; SPECIAL CASE FOR MINUS
  1200 0000153C 74ED                <1> 	je	short K45E		; GO TRANSLATE
  1201 0000153E 3C4E                <1> 	cmp	al , 78			; SPECIAL CASE FOR PLUS
  1202 00001540 74E9                <1> 	je	short K45E		; GO TRANSLATE
  1203 00001542 F6C702              <1> 	test	bh, LC_E0		; IS THIS ONE OFTHE NEW KEYS?
  1204 00001545 750A                <1> 	jnz	short K49		; YES, TRANSLATE TO BASE STATE
  1205                              <1> 	;		
  1206 00001547 F6C320              <1> 	test 	bl, NUM_STATE		; ARE WE IN NUM LOCK
  1207 0000154A 7514                <1> 	jnz	short K50		; TEST FOR SURE
  1208 0000154C F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; ARE WE IN SHIFT STATE?
  1209                              <1> 	;jnz	short K51		; IF SHIFTED, REALLY NUM STATE
  1210 0000154F 75DA                <1> 	jnz	short K45E
  1211                              <1> 	;
  1212                              <1> 	;-----	BASE CASE FOR KEYPAD
  1213                              <1> K49:					
  1214 00001551 3C4C                <1> 	cmp	al, 76			; SPECIAL CASE FOR BASE STATE 5
  1215 00001553 7504                <1> 	jne	short K49A		; CONTINUE IF NOT KEYPAD 5
  1216 00001555 B0F0                <1> 	mov	al, 0F0h		; SPECIAL ASCII CODE	
  1217 00001557 EB40                <1> 	jmp	short K57		; BUFFER FILL
  1218                              <1> K49A:
  1219 00001559 BB[94650000]        <1> 	mov	ebx, K10		; BASE CASE TABLE	
  1220 0000155E EB27                <1> 	jmp	short K64		; CONVERT TO PSEUDO SCAN
  1221                              <1> 	;
  1222                              <1> 	;-----	MIGHT BE NUM LOCK, TEST SHIFT STATUS
  1223                              <1> K50:					; ALMOST-NUM-STATE
  1224 00001560 F6C303              <1>         test    bl, LEFT_SHIFT+RIGHT_SHIFT
  1225 00001563 75EC                <1> 	jnz 	short K49		; SHIFTED TEMP OUT OF NUM STATE
  1226 00001565 EBC4                <1> K51:	jmp	short K45E		; REALLY NUM STATE
  1227                              <1> 	;
  1228                              <1> 	;-----	TEST FOR THE NEW KEYS ON WT KEYBOARDS 
  1229                              <1> K52:					; NOT A NUMPAD KEY
  1230 00001567 3C56                <1> 	cmp	al, 86			; IS IT THE NEW WT KEY?
  1231                              <1> 	;jne	short K53		; JUMP IF NOT
  1232                              <1> 	;jmp	short K45B		; HANDLE WITH REST OF LETTER KEYS
  1233 00001569 74AF                <1> 	je	short K45B		
  1234                              <1> 	;
  1235                              <1> 	;-----	MUST BE F11 OR F12 
  1236                              <1> K53:					; F1 - F10 COME HERE, TOO
  1237 0000156B F6C303              <1> 	test	bl, LEFT_SHIFT+RIGHT_SHIFT ; TEST SHIFT STATE
  1238 0000156E 74E1                <1> 	jz	short K49		; JUMP, LOWER CASE PSEUDO SC'S
  1239                              <1> 		; 20/02/2015 
  1240 00001570 BB[EC650000]        <1> 	mov	ebx, K11		; UPPER CASE PSEUDO SCAN CODES
  1241 00001575 EB10                <1> 	jmp	short K64		; TRANSLATE SCAN
  1242                              <1> 	;
  1243                              <1> 	;-----	TRANSLATE THE CHARACTER
  1244                              <1> K56:					; TRANSLATE-CHAR
  1245 00001577 FEC8                <1> 	dec	al			; CONVERT ORIGIN
  1246 00001579 D7                  <1> 	xlat    			; CONVERT THE SCAN CODE TO ASCII
  1247 0000157A F605[48660000]02    <1> 	test	byte [KB_FLAG_3], LC_E0	; IS THIS A NEW KEY?
  1248 00001581 7416                <1> 	jz	short K57		; NO, GO FILL BUFFER
  1249 00001583 B4E0                <1> 	mov	ah, MC_E0		; YES, PUT SPECIAL MARKER IN AH
  1250 00001585 EB12                <1> 	jmp	short K57		; PUT IT INTO THE BUFFER	
  1251                              <1> 	;
  1252                              <1> 	;-----	TRANSLATE SCAN FOR PSEUDO SCAN CODES
  1253                              <1> K64:					; TRANSLATE-SCAN-ORGD
  1254 00001587 FEC8                <1> 	dec	al			; CONVERT ORIGIN
  1255 00001589 D7                  <1>        	xlat    	                ; CTL TABLE SCAN
  1256 0000158A 88C4                <1> 	mov	ah, al			; PUT VALUE INTO AH
  1257 0000158C B000                <1> 	mov	al, 0			; ZERO ASCII CODE
  1258 0000158E F605[48660000]02    <1> 	test	byte [KB_FLAG_3], LC_E0	; IS THIS A NEW KEY?
  1259 00001595 7402                <1> 	jz	short K57		; NO, GO FILL BUFFER
  1260 00001597 B0E0                <1> 	mov	al, MC_E0		; YES, PUT SPECIAL MARKER IN AL
  1261                              <1> 	;
  1262                              <1> 	;-----	PUT CHARACTER INTO BUFFER
  1263                              <1> K57:					; BUFFER_FILL
  1264 00001599 3CFF                <1> 	cmp	al, -1			; IS THIS AN IGNORE CHAR
  1265                              <1>         ;je	short K59		; YES, DO NOTHING WITH IT
  1266 0000159B 0F8459FDFFFF        <1> 	je      K26			; YES, DO NOTHING WITH IT
  1267 000015A1 80FCFF              <1> 	cmp	ah, -1			; LOOK FOR -1 PSEUDO SCAN
  1268                              <1>         ;jne	short K61		; NEAR_INTERRUPT_RETURN
  1269 000015A4 0F8450FDFFFF        <1> 	je      K26			; INTERRUPT_RETURN
  1270                              <1> ;K59:					; NEAR_INTERRUPT_RETURN
  1271                              <1> ;	jmp	K26			; INTERRUPT_RETURN
  1272                              <1> 
  1273                              <1> _K60: ; 29/01/2016
  1274 000015AA 80FC68              <1> 	cmp	ah, 68h	; ALT + F1 key
  1275 000015AD 721F                <1> 	jb	short K61
  1276 000015AF 80FC6F              <1> 	cmp	ah, 6Fh ; ALT + F8 key	
  1277 000015B2 771A                <1> 	ja	short K61
  1278                              <1> 	;
  1279 000015B4 8A1D[AE5E0100]      <1> 	mov	bl, [ACTIVE_PAGE]
  1280 000015BA 80C368              <1> 	add	bl, 68h
  1281 000015BD 38E3                <1> 	cmp	bl, ah
  1282 000015BF 740D                <1> 	je	short K61
  1283 000015C1 6650                <1> 	push	ax
  1284 000015C3 88E0                <1> 	mov	al, ah
  1285 000015C5 2C68                <1> 	sub	al, 68h
  1286 000015C7 E8B2070000          <1> 	call	set_active_page
  1287 000015CC 6658                <1> 	pop	ax
  1288                              <1> K61:					; NOT-CAPS-STATE
  1289 000015CE 8B1D[56660000]      <1> 	mov	ebx, [BUFFER_TAIL] 	; GET THE END POINTER TO THE BUFFER
  1290 000015D4 89DE                <1> 	mov	esi, ebx		; SAVE THE VALUE
  1291 000015D6 E857FAFFFF          <1> 	call	_K4			; ADVANCE THE TAIL
  1292 000015DB 3B1D[52660000]      <1> 	cmp	ebx, [BUFFER_HEAD] 	; HAS THE BUFFER WRAPPED AROUND
  1293 000015E1 740E                <1> 	je	short K62		; BUFFER_FULL_BEEP
  1294 000015E3 668906              <1> 	mov	[esi], ax		; STORE THE VALUE
  1295 000015E6 891D[56660000]      <1> 	mov	[BUFFER_TAIL], ebx 	; MOVE THE POINTER UP
  1296 000015EC E909FDFFFF          <1> 	jmp	K26
  1297                              <1> 	;;cli				; TURN OFF INTERRUPTS
  1298                              <1> 	;;mov	al, EOI			; END OF INTERRUPT COMMAND
  1299                              <1> 	;;out	INTA00, al		; SEND COMMAND TO INTERRUPT CONTROL PORT
  1300                              <1> 	;MOV	AL, ENA_KBD		; INSURE KEYBOARD IS ENABLED
  1301                              <1> 	;CALL	SHIP_IT			; EXECUTE ENABLE
  1302                              <1> 	;MOV	AX, 9102H		; MOVE IN POST CODE & TYPE
  1303                              <1> 	;INT	15H			; PERFORM OTHER FUNCTION
  1304                              <1> 	;;and	byte [KB_FLAG_3],~(LC_E0+LC_E1) ; RESET LAST CHAR H.C. FLAG
  1305                              <1> 	;JMP	K27A			; INTERRUPT_RETURN
  1306                              <1> 	;;jmp   K27                    
  1307                              <1> 	;
  1308                              <1> 	;-----	BUFFER IS FULL SOUND THE BEEPER
  1309                              <1> K62:
  1310 000015F1 B020                <1> 	mov	al, EOI			; ENABLE INTERRUPT CONTROLLER CHIP
  1311 000015F3 E620                <1> 	out	INTA00, al
  1312 000015F5 66B9A602            <1> 	mov	cx, 678			; DIVISOR FOR 1760 HZ
  1313 000015F9 B304                <1> 	mov	bl, 4			; SHORT BEEP COUNT (1/16 + 1/64 DELAY)
  1314 000015FB E8CC0B0000          <1> 	call	beep			; GO TO COMMON BEEP HANDLER
  1315 00001600 E901FDFFFF          <1> 	jmp     K27			; EXIT   
  1316                              <1> 
  1317                              <1> SHIP_IT:
  1318                              <1> 	;---------------------------------------------------------------------------------
  1319                              <1> 	; SHIP_IT
  1320                              <1> 	;	THIS ROUTINES HANDLES TRANSMISSION OF COMMAND AND DATA BYTES
  1321                              <1> 	;	TO THE KEYBOARD CONTROLLER.
  1322                              <1> 	;---------------------------------------------------------------------------------
  1323                              <1> 	;
  1324 00001605 6650                <1> 	push	ax			; SAVE DATA TO SEND
  1325                              <1> 
  1326                              <1> 	;-----	WAIT FOR COMMAND TO ACCEPTED
  1327 00001607 FA                  <1> 	cli				; DISABLE INTERRUPTS TILL DATA SENT
  1328                              <1> 	; xor	ecx, ecx		; CLEAR TIMEOUT COUNTER
  1329 00001608 B900000100          <1> 	mov	ecx, 10000h			
  1330                              <1> S10:
  1331 0000160D E464                <1> 	in	al, STATUS_PORT		; READ KEYBOARD CONTROLLER STATUS
  1332 0000160F A802                <1> 	test	al, INPT_BUF_FULL	; CHECK FOR ITS INPUT BUFFER BUSY
  1333 00001611 E0FA                <1> 	loopnz	S10			; WAIT FOR COMMAND TO BE ACCEPTED
  1334                              <1> 
  1335 00001613 6658                <1> 	pop	ax			; GET DATA TO SEND
  1336 00001615 E664                <1> 	out	STATUS_PORT, al		; SEND TO KEYBOARD CONTROLLER
  1337 00001617 FB                  <1> 	sti				; ENABLE INTERRUPTS AGAIN
  1338 00001618 C3                  <1> 	retn				; RETURN TO CALLER
  1339                              <1> 
  1340                              <1> SND_DATA:
  1341                              <1> 	; ---------------------------------------------------------------------------------
  1342                              <1> 	; SND_DATA
  1343                              <1> 	;	THIS ROUTINES HANDLES TRANSMISSION OF COMMAND AND DATA BYTES
  1344                              <1> 	;	TO THE KEYBOARD AND RECEIPT OF ACKNOWLEDGEMENTS. IT ALSO
  1345                              <1> 	;	HANDLES ANY RETRIES IF REQUIRED
  1346                              <1> 	; ---------------------------------------------------------------------------------
  1347                              <1> 	;
  1348 00001619 6650                <1> 	push	ax			; SAVE REGISTERS
  1349 0000161B 6653                <1> 	push	bx
  1350 0000161D 51                  <1> 	push	ecx
  1351 0000161E 88C7                <1> 	mov	bh, al			; SAVE TRANSMITTED BYTE FOR RETRIES
  1352 00001620 B303                <1> 	mov	bl, 3			; LOAD RETRY COUNT
  1353                              <1> SD0:
  1354 00001622 FA                  <1> 	cli				; DISABLE INTERRUPTS
  1355 00001623 8025[47660000]CF    <1> 	and	byte [KB_FLAG_2], ~(KB_FE+KB_FA) ; CLEAR ACK AND RESEND FLAGS
  1356                              <1> 	;
  1357                              <1> 	;-----	WAIT FOR COMMAND TO BE ACCEPTED
  1358 0000162A B900000100          <1> 	mov	ecx, 10000h		; MAXIMUM WAIT COUNT
  1359                              <1> SD5:
  1360 0000162F E464                <1> 	in	al, STATUS_PORT		; READ KEYBOARD PROCESSOR STATUS PORT
  1361 00001631 A802                <1> 	test	al, INPT_BUF_FULL	; CHECK FOR ANY PENDING COMMAND
  1362 00001633 E0FA                <1> 	loopnz	SD5			; WAIT FOR COMMAND TO BE ACCEPTED
  1363                              <1> 	;
  1364 00001635 88F8                <1> 	mov	al, bh			; REESTABLISH BYTE TO TRANSMIT
  1365 00001637 E660                <1> 	out	PORT_A, al		; SEND BYTE
  1366 00001639 FB                  <1> 	sti				; ENABLE INTERRUPTS
  1367                              <1> 	;mov	cx, 01A00h		; LOAD COUNT FOR 10 ms+
  1368 0000163A B9FFFF0000          <1> 	mov	ecx, 0FFFFh
  1369                              <1> SD1:
  1370 0000163F F605[47660000]30    <1> 	test	byte [KB_FLAG_2], KB_FE+KB_FA ; SEE IF EITHER BIT SET
  1371 00001646 750F                <1> 	jnz	short SD3		; IF SET, SOMETHING RECEIVED GO PROCESS
  1372 00001648 E2F5                <1> 	loop	SD1			; OTHERWISE WAIT
  1373                              <1> SD2:
  1374 0000164A FECB                <1> 	dec	bl			; DECREMENT RETRY COUNT
  1375 0000164C 75D4                <1> 	jnz	short SD0		; RETRY TRANSMISSION
  1376 0000164E 800D[47660000]80    <1> 	or	byte [KB_FLAG_2], KB_ERR ; TURN ON TRANSMIT ERROR FLAG
  1377 00001655 EB09                <1> 	jmp	short SD4		; RETRIES EXHAUSTED FORGET TRANSMISSION
  1378                              <1> SD3:
  1379 00001657 F605[47660000]10    <1> 	test	byte [KB_FLAG_2], KB_FA ; SEE IF THIS IS AN ACKNOWLEDGE
  1380 0000165E 74EA                <1> 	jz	short SD2		; IF NOT, GO RESEND
  1381                              <1> SD4:	
  1382 00001660 59                  <1> 	pop	ecx			; RESTORE REGISTERS
  1383 00001661 665B                <1> 	pop	bx
  1384 00001663 6658                <1> 	pop	ax
  1385 00001665 C3                  <1> 	retn				; RETURN, GOOD TRANSMISSION
  1386                              <1> 
  1387                              <1> SND_LED:
  1388                              <1> 	; ---------------------------------------------------------------------------------
  1389                              <1> 	; SND_LED
  1390                              <1> 	;	THIS ROUTINES TURNS ON THE MODE INDICATORS.
  1391                              <1> 	;
  1392                              <1> 	;----------------------------------------------------------------------------------
  1393                              <1> 	;
  1394 00001666 FA                  <1> 	cli				; TURN OFF INTERRUPTS
  1395 00001667 F605[47660000]40    <1> 	test	byte [KB_FLAG_2], KB_PR_LED ; CHECK FOR MODE INDICATOR UPDATE
  1396 0000166E 755F                <1> 	jnz 	short SL1		; DON'T UPDATE AGAIN IF UPDATE UNDERWAY
  1397                              <1> 	;
  1398 00001670 800D[47660000]40    <1> 	or	byte [KB_FLAG_2], KB_PR_LED ; TURN ON UPDATE IN PROCESS
  1399 00001677 B020                <1> 	mov	al, EOI			; END OF INTERRUPT COMMAND
  1400 00001679 E620                <1> 	out	20h, al ;out INTA00, al	; SEND COMMAND TO INTERRUPT CONTROL PORT
  1401 0000167B EB11                <1> 	jmp	short SL0		; GO SEND MODE INDICATOR COMMAND
  1402                              <1> SND_LED1:
  1403 0000167D FA                  <1> 	cli				; TURN OFF INTERRUPTS
  1404 0000167E F605[47660000]40    <1> 	test	byte [KB_FLAG_2], KB_PR_LED ; CHECK FOR MODE INDICATOR UPDATE
  1405 00001685 7548                <1> 	jnz	short SL1		; DON'T UPDATE AGAIN IF UPDATE UNDERWAY
  1406                              <1> 	;
  1407 00001687 800D[47660000]40    <1> 	or	byte [KB_FLAG_2], KB_PR_LED ; TURN ON UPDATE IN PROCESS
  1408                              <1> SL0:
  1409 0000168E B0ED                <1> 	mov	al, LED_CMD		; LED CMD BYTE
  1410 00001690 E884FFFFFF          <1> 	call	SND_DATA		; SEND DATA TO KEYBOARD
  1411 00001695 FA                  <1> 	cli
  1412 00001696 E836000000          <1> 	call	MAKE_LED		; GO FORM INDICATOR DATA BYTE
  1413 0000169B 8025[47660000]F8    <1> 	and	byte [KB_FLAG_2], 0F8h	; ~KB_LEDS ; CLEAR MODE INDICATOR BITS
  1414 000016A2 0805[47660000]      <1> 	or	[KB_FLAG_2], al 	; SAVE PRESENT INDICATORS FOR NEXT TIME
  1415 000016A8 F605[47660000]80    <1> 	test	byte [KB_FLAG_2], KB_ERR ; TRANSMIT ERROR DETECTED
  1416 000016AF 750F                <1> 	jnz	short SL2		; IF SO, BYPASS SECOND BYTE TRANSMISSION
  1417                              <1> 	;
  1418 000016B1 E863FFFFFF          <1> 	call	SND_DATA		; SEND DATA TO KEYBOARD
  1419 000016B6 FA                  <1> 	cli				; TURN OFF INTERRUPTS
  1420 000016B7 F605[47660000]80    <1> 	test	byte [KB_FLAG_2], KB_ERR ; TRANSMIT ERROR DETECTED
  1421 000016BE 7408                <1> 	jz	short SL3		; IF NOT, DON'T SEND AN ENABLE COMMAND
  1422                              <1> SL2:
  1423 000016C0 B0F4                <1> 	mov	al, KB_ENABLE		; GET KEYBOARD CSA ENABLE COMMAND
  1424 000016C2 E852FFFFFF          <1> 	call	SND_DATA		; SEND DATA TO KEYBOARD
  1425 000016C7 FA                  <1> 	cli				; TURN OFF INTERRUPTS
  1426                              <1> SL3:
  1427 000016C8 8025[47660000]3F    <1> 	and	byte [KB_FLAG_2], ~(KB_PR_LED+KB_ERR) ; TURN OFF MODE INDICATOR
  1428                              <1> SL1:					; UPDATE AND TRANSMIT ERROR FLAG
  1429 000016CF FB                  <1> 	sti				; ENABLE INTERRUPTS
  1430 000016D0 C3                  <1> 	retn				; RETURN TO CALLER
  1431                              <1> 
  1432                              <1> MAKE_LED:
  1433                              <1> 	;---------------------------------------------------------------------------------
  1434                              <1> 	; MAKE_LED
  1435                              <1> 	;	THIS ROUTINES FORMS THE DATA BYTE NECESSARY TO TURN ON/OFF
  1436                              <1> 	;	THE MODE INDICATORS.
  1437                              <1> 	;---------------------------------------------------------------------------------
  1438                              <1> 	;
  1439                              <1> 	;push 	cx			; SAVE CX
  1440 000016D1 A0[45660000]        <1> 	mov	al, [KB_FLAG]		; GET CAPS & NUM LOCK INDICATORS
  1441 000016D6 2470                <1> 	and	al, CAPS_STATE+NUM_STATE+SCROLL_STATE ; ISOLATE INDICATORS
  1442                              <1> 	;mov	cl, 4			; SHIFT COUNT
  1443                              <1> 	;rol	al, cl			; SHIFT BITS OVER TO TURN ON INDICATORS
  1444 000016D8 C0C004              <1> 	rol	al, 4 ; 20/02/2015
  1445 000016DB 2407                <1> 	and	al, 07h			; MAKE SURE ONLY MODE BITS ON
  1446                              <1> 	;pop	cx
  1447 000016DD C3                  <1> 	retn				; RETURN TO CALLER
  1448                              <1> 
  1449                              <1> ; % include 'kybdata.s'   ; KEYBOARD DATA
  1450                              <1> 
  1451                              <1> 
  1452                              <1> ; /// End Of KEYBOARD FUNCTIONS ///
  2456                                  
  2457                                  %include 'video.s' ; 07/03/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.3 - video.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 30/11/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 16/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; video.inc (13/08/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-AT' BIOS source code (1985) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - VIDEO.INC
    20                              <1> ; Last Modification: 13/08/2015
    21                              <1> ;		  (Video Data is in 'VIDATA.INC')
    22                              <1> ;
    23                              <1> ; ///////// VIDEO (CGA) FUNCTIONS ///////////////
    24                              <1> 
    25                              <1> ; 16/01/2016 (32 bit modifications, TRDOS386 - TRDOS v2.0, video.s)
    26                              <1> ; INT 31H (TRDOS 386) = INT 10H (IBM PC/AT REAL MODE)
    27                              <1> 
    28                              <1> ; IBM PC-AT BIOS Source Code
    29                              <1> ; TITLE VIDEO1 --- 06/10/85  VIDEO DISPLAY BIOS
    30                              <1> 
    31                              <1> _int10h:
    32                              <1> 	; 23/03/2016
    33                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
    34 000016DE 9C                  <1> 	pushfd
    35 000016DF 0E                  <1> 	push	cs
    36 000016E0 E851000000          <1> 	call	VIDEO_IO_1
    37 000016E5 C3                  <1> 	retn
    38                              <1> 
    39                              <1> ;--- INT 10 H -------------------------------------------------------------------
    40                              <1> ; VIDEO_IO									:	
    41                              <1> ;	THESE ROUTINES PROVIDE THE CRT DISPLAY INTERFACE			:
    42                              <1> ;	THE FOLLOWING FUNCTIONS ARE PROVIDED:					:
    43                              <1> ;										:
    44                              <1> ;    (AH)= 00H	SET MODE (AL) CONTAINS MODE VALUE				:
    45                              <1> ;		(AL) = 00H  40X25 BW MODE (POWER ON DEFAULT)			:
    46                              <1> ;		(AL) = 01H  40X25 COLOR						:
    47                              <1> ;		(AL) = 02H  80X25 BW						:
    48                              <1> ;		(AL) = 03H  80X25 COLOR						:
    49                              <1> ;		              GRAPHICS MODES					:
    50                              <1> ;		(AL) = 04H  320X200 COLOR					:
    51                              <1> ;		(AL) = 05H  320X200 BW MODE					:
    52                              <1> ;		(AL) = 06H  640X200 BW MODE					:
    53                              <1> ;		(AL) = 07H   80X25 MONOCHROME (USED INTERNAL TO VIDEO ONLY)	:
    54                              <1> ;		*** NOTES -BW MODES OPERATE SAME AS COLOR MODES, BUT COLOR	:
    55                              <1> ;		           BURST IS NOT ENABLED					:
    56                              <1> ;		          -CURSOR IS NOT DISPLAYED IN GRAPHICS MODE		:
    57                              <1> ;    (AH)= 01H	SET CURSOR TYPE							:
    58                              <1> ;		(CH) = BITS 4-0 = START LINE FOR CURSOR				:
    59                              <1> ;		       ** HARDWARE WILL ALWAYS CAUSE BLINK			:
    60                              <1> ;		       ** SETTING BIT 5 OR 6 WILL CAUSE ERRATIC BLINKING	:
    61                              <1> ;		          OR NO CURSOR AT ALL					:
    62                              <1> ;		(CL) = BITS 4-0 = END LINE FOR CURSOR				:
    63                              <1> ;    (AH)= 02H	SET CURSOR POSITION						:
    64                              <1> ;		(DH,DL) = ROW,COLUMN  (00H,00H) IS UPPER LEFT			:
    65                              <1> ;		(BH) = A PAGE NUMBER (MUST BE 00H FOR GRAPHICS MODES)		:
    66                              <1> ;    (AH)= 03H	READ CURSOR POSITION						:
    67                              <1> ;		(BH) = PAGE NUMBER (MUST BE 00H FOR GRAPHICS MODES)		:
    68                              <1> ;		ON EXIT (DH,DL) = ROW,COLUMN OF CURRENT CURSOR			:
    69                              <1> ;		        (CH,CL) = CURSOR MODE CURRENTLY SET			:
    70                              <1> ;    (AH)= 04H	READ LIGHT PEN POSITION						:
    71                              <1> ;		ON EXIT:							:
    72                              <1> ;		(AH) = 00H -- LIGHT PEN SWITCH NOT DOWN/NOT TRIGGERED		:
    73                              <1> ;		(AH) = 01H -- VALID LIGHT PEN VALUE IN REGISTERS		:
    74                              <1> ;		        (DH,DL) = ROW,COLUMN OF CHARACTER LP POSITION		:
    75                              <1> ;		        (CH) = RASTER LINE (0-199)				:
    76                              <1> ;		        (BX) = PIXEL COLUMN (0-319,639)				:
    77                              <1> ;    (AH)= 05H	SELECT ACTIVE DISPLAY PAGE (VALID ONLY FOR ALPHA MODES)		:
    78                              <1> ;		(AL) = NEW PAGE VALUE (0-7 FOR MODES 0&1, 0-3 FOR MODES 2&3)	:
    79                              <1> ;    (AH)= 06H	SCROLL ACTIVE PAGE UP						:
    80                              <1> ;		(AL) = NUMBER OF LINES. ( LINES BLANKED AT BOTTOM OF WINDOW )	:
    81                              <1> ;		        (AL) = 00H MEANS BLANK ENTIRE WINDOW			:
    82                              <1> ;		(CH,CL) = ROW,COLUMN OF UPPER LEFT CORNER OF SCROLL		:
    83                              <1> ;		(DH,DL) = ROW,COLUMN OF LOWER RIGHT CORNER OF SCROLL		:
    84                              <1> ;		(BH) = ATTRIBUTE TO BE USED ON BLANK LINE			:
    85                              <1> ;    (AH)= 07H	SCROLL ACTIVE PAGE DOWN						:
    86                              <1> ;		(AL) = NUMBER OF LINES, INPUT LINES BLANKED AT TOP OF WINDOW	:
    87                              <1> ;		        (AL) = 00H MEANS BLANK ENTIRE WINDOW			:
    88                              <1> ;		(CH,CL) = ROW,COLUMN OF UPPER LEFT CORNER OF SCROLL		:
    89                              <1> ;		(DH,DL) = ROW,COLUMN OF LOWER RIGHT CORNER OF SCROLL		:
    90                              <1> ;		(BH) = ATTRIBUTE TO BE USED ON BLANK LINE			:
    91                              <1> ;										:
    92                              <1> ;   CHARACTER HANDLING ROUTINES							:
    93                              <1> ;										:
    94                              <1> ;    (AH)= 08H	READ ATTRIBUTE/CHARACTER AT CURRENT CURSOR POSITION		:
    95                              <1> ;		(BH) = DISPLAY PAGE (VALID FOR ALPHA MODES ONLY)		:
    96                              <1> ;		ON EXIT:							:
    97                              <1> ;		(AL) = CHAR READ						:
    98                              <1> ;		(AH) = ATTRIBUTE OF CHARACTER READ (ALPHA MODES ONLY)		:
    99                              <1> ;    (AH)= 09H	WRITE ATTRIBUTE/CHARACTER AT CURRENT CURSOR POSITION		:
   100                              <1> ;		(BH) = DISPLAY PAGE (VALID FOR ALPHA MODES ONLY)		:
   101                              <1> ;		(CX) = COUNT OF CHARACTERS TO WRITE				:
   102                              <1> ;		(AL) = CHAR TO WRITE						:
   103                              <1> ;		(BL) = ATTRIBUTE OF CHARACTER (ALPHA)/COLOR OF CHAR (GRAPHICS)	:
   104                              <1> ;		         SEE NOTE ON WRITE DOT FOR BIT 7 OF BL = 1.		:
   105                              <1> ;    (AH) = 0AH	WRITE CHARACTER ONLY AT CURRENT CURSOR POSITION			:
   106                              <1> ;		(BH) = DISPLAY PAGE (VALID FOR ALPHA MODES ONLY)		:
   107                              <1> ;		(CX) = COUNT OF CHARACTERS TO WRITE				:
   108                              <1> ;		(AL) = CHAR TO WRITE						:
   109                              <1> ;		       NOTE: USE FUNCTION (AH)= 09H IN GRAPHICS MODES		:
   110                              <1> ;	FOR READ/WRITE CHARACTER INTERFACE WHILE IN GRAPHICS MODE, THE		:
   111                              <1> ;		CHARACTERS ARE FORMED FROM A CHARACTER GENERATOR IMAGE		:
   112                              <1> ;		MAINTAINED IN THE SYSTEM ROM. ONLY THE 1ST 128 CHARS		:
   113                              <1> ;		ARE CONTAINED THERE. TO READ/WRITE THE SECOND 128 CHARS,	:
   114                              <1> ;		THE USER MUST INITIALIZE THE POINTER AT INTERRUPT 1FH		:
   115                              <1> ;		(LOCATION 0007CH) TO POINT TO THE 1K BYTE TABLE CONTAINING	:
   116                              <1> ;		THE CODE POINTS FOR THE SECOND 128 CHARS (128-255).		:
   117                              <1> ;	FOR WRITE CHARACTER INTERFACE IN GRAPHICS MODE, THE REPLICATION FACTOR	:
   118                              <1> ;		CONTAINED IN (CX) ON ENTRY WILL PRODUCE VALID RESULTS ONLY	:
   119                              <1> ;		FOR CHARACTERS CONTAINED ON THE SAME ROW. CONTINUATION TO	:
   120                              <1> ;		SUCCEEDING LINES WILL NOT PRODUCE CORRECTLY.			:
   121                              <1> ;										:
   122                              <1> ;    GRAPHICS INTERFACE								:
   123                              <1> ;    (AH)= 0BH	SET COLOR PALETTE						:
   124                              <1> ;		(BH) = PALETTE COLOR ID BEING SET (0-127)			:
   125                              <1> ;		(BL) = COLOR VALUE TO BE USED WITH THAT COLOR ID		:
   126                              <1> ;		       NOTE: FOR THE CURRENT COLOR CARD, THIS ENTRY POINT HAS	:
   127                              <1> ;		               MEANING ONLY FOR 320X200 GRAPHICS.		:
   128                              <1> ;		       COLOR ID = 0 SELECTS THE BACKGROUND COLOR (0-15)		:
   129                              <1> ;		       COLOR ID = 1 SELECTS THE PALETTE TO BE USED:		:
   130                              <1> ;		               0 = GREEN(1)/RED(2)/YELLOW(3)			:
   131                              <1> ;		               1 = CYAN(1)/MAGENTA(2)/WHITE(3)			:
   132                              <1> ;		       IN 40X25 OR 80X25 ALPHA MODES, THE VALUE SET FOR 	:
   133                              <1> ;		               PALETTE COLOR 0 INDICATES THE BORDER COLOR	:
   134                              <1> ;		               TO BE USED (VALUES 0-31, WHERE 16-31 SELECT	:
   135                              <1> ;		               THE HIGH INTENSITY BACKGROUND SET.		:
   136                              <1> ;    (AH)= 0CH	WRITE DOT							:
   137                              <1> ;		(DX) = ROW NUMBER						:
   138                              <1> ;		(CX) = COLUMN NUMBER						:
   139                              <1> ;		(AL) = COLOR VALUE						:
   140                              <1> ;		        IF BIT 7 OF AL = 1, THEN THE COLOR VALUE IS EXCLUSIVE	:
   141                              <1> ;		        ORed WITH THE CURRENT CONTENTS OF THE DOT		:
   142                              <1> ;    (AH)= ODH	READ DOT							:
   143                              <1> ;		(DX) = ROW NUMBER						:
   144                              <1> ;		(CX) = COLUMN NUMBER						:
   145                              <1> ;		(AL) = RETURNS THE DOT READ					:
   146                              <1> ;										:
   147                              <1> ;    ASCII TELETYPE ROUTINE FOR OUTPUT						:
   148                              <1> ;										:
   149                              <1> ;    (AH)= 0EH	WRITE TELETYPE TO ACTIVE PAGE					:
   150                              <1> ;		(AL) = CHAR TO WRITE						:
   151                              <1> ;		(BL) = FOREGROUND COLOR IN GRAPHICS MODE			:
   152                              <1> ;		NOTE -- SCREEN WIDTH IS CONTROLLED BY PREVIOUS MODE SET		:
   153                              <1> ;    (AH)= 0FH	CURRENT VIDEO STATE						:
   154                              <1> ;		RETURNS THE CURRENT VIDEO STATE					:
   155                              <1> ;		(AL) = MODE CURRENTLY SET ( SEE (AH)=00H FOR EXPLANATION)	:
   156                              <1> ;		(AH) = NUMBER OR CHARACTER COLUMNS ON SCREEN			:
   157                              <1> ;		(BH) = CURRENT ACTIVE DISPLAY PAGE				:
   158                              <1> ;    (AH)= 10H	RESERVED							:
   159                              <1> ;    (AH)= 11H	RESERVED							:
   160                              <1> ;    (AH)= 12H	RESERVED							:
   161                              <1> ;    (AH)= 13H	WRITE STRING							:
   162                              <1> ;			ES:BP  -  POINTER T0 STRING TO BE WRITTEN		:
   163                              <1> ;			CX     -  LENGTH OF CHARACTER STRING TO WRITTEN		:
   164                              <1> ;			DX     -  CURSOR POSITION FOR STRING TO BE WRITTEN	:
   165                              <1> ;			BH     -  PAGE NUMBER					:
   166                              <1> ;		(AL)= 00H	WRITE CHARACTER STRING				:
   167                              <1> ;			BL     -  ATTRIBUTE					:
   168                              <1> ;			STRING IS  <CHAR,CHAR, ... ,CHAR>			:
   169                              <1> ;			CURSOR NOT MOVED					:
   170                              <1> ;		(AL)= 01H	WRITE CHARACTER STRING AND MOVE CURSOR		:
   171                              <1> ;			BL     -  ATTRIBUTE					:
   172                              <1> ;			STRING IS  <CHAR,CHAR, ... ,CHAR>			:
   173                              <1> ;			CURSOR MOVED						:
   174                              <1> ;		(AL)= 02H	WRITE CHARACTER AND ATTRIBUTE STRING		:
   175                              <1> ;			       (VALID FOR ALPHA MODES ONLY)			:
   176                              <1> ;			STRING IS <CHAR,ATTR,CHAR,ATTR ..  ,CHAR,ATTR>		:
   177                              <1> ;			CURSOR IS NOT MOVED					:
   178                              <1> ;		(AL)= 03H WRITE CHARACTER AND ATTRIBUTE STRING AND MOVE CURSOR	:
   179                              <1> ;			       (VALID FOR ALPHA MODES ONLY)			:
   180                              <1> ;			STRING IS <CHAR,ATTR,CHAR,ATTR ..  ,CHAR,ATTR>		:
   181                              <1> ;			CURSOR IS MOVED						:
   182                              <1> ;		 NOTE:  CARRIAGE RETURN, LINE FEED, BACKSPACE, AND BELL ARE	:
   183                              <1> ;		        TREATED AS COMMANDS RATHER THAN PRINTABLE CHARACTERS.	:
   184                              <1> ;										:
   185                              <1> ;	BX,CX,DX,SI,DI,BP,SP,DS,ES,SS PRESERVED DURING CALLS EXCEPT FOR		:
   186                              <1> ;	BX,CX,DX RETURN VALUES ON FUNCTIONS 03H,04H,0DH AND 0FH. ON ALL CALLS	:
   187                              <1> ;	AX IS MODIFIED.								:
   188                              <1> ;--------------------------------------------------------------------------------
   189                              <1> 
   190 000016E6 [21190000]          <1> M1:	dd	SET_MODE	; TABLE OF ROUTINES WITHIN VIDEO I/O
   191 000016EA [BE1C0000]          <1> 	dd	SET_CTYPE
   192 000016EE [F21C0000]          <1> 	dd	SET_CPOS
   193 000016F2 [1A1D0000]          <1> 	dd	READ_CURSOR
   194                              <1> 	;dd	VIDEO_RETURN	; READ_LPEN
   195 000016F6 [1F190000]          <1> 	dd	set_mode_ncm	; Set mode without clearing video memory
   196 000016FA [601D0000]          <1> 	dd	ACT_DISP_PAGE
   197 000016FE [F21D0000]          <1> 	dd	SCROLL_UP
   198 00001702 [1C1F0000]          <1> 	dd	SCROLL_DOWN
   199 00001706 [9C1F0000]          <1> 	dd	READ_AC_CURRENT
   200 0000170A [02200000]          <1> 	dd	WRITE_AC_CURRENT
   201 0000170E [28200000]          <1> 	dd	WRITE_C_CURRENT
   202 00001712 [6B290000]          <1> 	dd	SET_COLOR
   203 00001716 [D6290000]          <1> 	dd	WRITE_DOT
   204 0000171A [A1290000]          <1> 	dd	READ_DOT
   205 0000171E [B8200000]          <1> 	dd	WRITE_TTY
   206 00001722 [07190000]          <1> 	dd	VIDEO_STATE
   207 00001726 [1F330000]          <1> 	dd	vga_pal_funcs ; 10/08/2016 (TRDOS 386)
   208 0000172A [D72E0000]          <1> 	dd	font_setup    ; 10/07/2016 (TRDOS 386)
   209 0000172E [56190000]          <1> 	dd	VIDEO_RETURN	; RESERVED
   210 00001732 [2D220000]          <1> 	dd	WRITE_STRING  ; 23/06/2016 (TRDOS 386)
   211                              <1> M1L	EQU	$ - M1
   212                              <1> 
   213                              <1> ; 27/11/2020 - TRDOS 386 v2.0.3
   214                              <1> ; 14/01/2017
   215                              <1> ; 02/01/2017
   216                              <1> ; 04/07/2016
   217                              <1> ; 12/05/2016
   218                              <1> ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   219                              <1> int31h:  ; Video BIOS
   220                              <1> 
   221                              <1> ; BH = Video page number
   222                              <1> ; BL = Color/Attribute
   223                              <1> ; AH = Function number
   224                              <1> ; AL = Character
   225                              <1> 
   226                              <1> VIDEO_IO_1:
   227                              <1> 	;sti				; INTERRUPTS BACK ON
   228 00001736 FC                  <1> 	cld				; SET DIRECTION FORWARD
   229                              <1> 	
   230                              <1> 	;cmp	ah, M1L/4		; TEST FOR WITHIN TABLE RANGE
   231                              <1> 	;jnb	short M4		; BRANCH TO EXIT IF NOT A VALID COMMAND
   232                              <1> 
   233                              <1> 	; 26/11/2020
   234 00001737 80FC14              <1> 	cmp	ah, M1L/4
   235 0000173A 7205                <1> 	jb	short VGA_func
   236                              <1> 
   237 0000173C 80FC4F              <1> 	cmp	ah, 4Fh
   238 0000173F 753B                <1> 	jne	short M4 ; invalid !
   239                              <1> 
   240                              <1> VGA_func: ; 26/11/2020
   241 00001741 06                  <1> 	push	es ; *
   242 00001742 1E                  <1> 	push	ds ; **			; SAVE WORK AND PARAMETER REGISTERS
   243                              <1> 
   244                              <1> 	; 26/11/2020
   245 00001743 50                  <1> 	push	eax ; -
   246                              <1> 	
   247 00001744 66B81000            <1> 	mov	ax, KDATA 		; POINT DS: TO DATA SEGMENT
   248 00001748 8ED8                <1> 	mov	ds, ax
   249 0000174A 8EC0                <1> 	mov	es, ax
   250                              <1> 
   251                              <1> 	; 26/11/2020
   252 0000174C 58                  <1> 	pop	eax ; +
   253                              <1> 	;
   254 0000174D FB                  <1> 	sti
   255 0000174E 80FC4F              <1> 	cmp	ah, 4Fh
   256 00001751 742A                <1> 	je	short VBE_func
   257                              <1> 
   258                              <1> 	; 28/11/2020
   259 00001753 803D[9C110300]00    <1> 	cmp	byte [pmi32], 0		; 32 bit protected mode interface for
   260 0000175A 0F8798000000        <1> 	ja	vesa_vbe3_pmi		; video hardware's vga bios firmware
   261                              <1> 					; ([pmi32] > 0 if it is activated)
   262                              <1> 					; note:
   263                              <1> vbe3_pmi_0: ; return back from vbe3_pmi	; [vbe3] = 3 is required to activate
   264                              <1> 
   265 00001760 52                  <1> 	push	edx ; ***
   266 00001761 51                  <1> 	push	ecx ; ****
   267 00001762 53                  <1> 	push	ebx ; *****
   268 00001763 56                  <1> 	push	esi ; ******
   269 00001764 57                  <1> 	push	edi ; *******
   270 00001765 55                  <1> 	push	ebp ; ********
   271                              <1> 
   272 00001766 A3[086B0100]        <1> 	mov	[video_eax], eax ; 12/05/2016 
   273 0000176B BF00800B00          <1> 	mov	edi, 0B8000h		; GET offset FOR COLOR CARD
   274                              <1> 
   275                              <1> 	; 23/03/2016
   276 00001770 C0E402              <1> 	shl	ah, 2  ; dword		; TIMES 2 FOR WORD TABLE LOOKUP
   277 00001773 0FB6F4              <1> 	movzx	esi, ah			; MOVE OFFSET INTO LOOK UP REGISTER (SI)
   278                              <1> 	;mov	ah, [CRT_MODE]		; MOVE CURRENT MODE INTO (AH) REGISTER
   279                              <1> 
   280                              <1> 	;;15/01/2017
   281                              <1> 	; 14/01/2017
   282                              <1> 	; 02/01/2017
   283                              <1> 	;;mov	byte [intflg], 31h  ; video interrupt
   284                              <1> 	;sti ; 26/11/2020
   285                              <1> 	;
   286                              <1> 
   287 00001776 FFA6[E6160000]      <1> 	JMP	dword [esi+M1]		; GO TO SELECTED FUNCTION
   288                              <1> M4:
   289                              <1> 					; COMMAND NOT VALID
   290 0000177C CF                  <1> 	iretd				; DO NOTHING IF NOT IN VALID RANGE
   291                              <1> 
   292                              <1> VBE_func:
   293                              <1> 	; 26/11/2020
   294                              <1> 	;sti
   295 0000177D 55                  <1> 	push	ebp ; *** ; 27/11/2020	
   296 0000177E 56                  <1> 	push	esi ; **** 
   297                              <1> 	
   298                              <1> 	; Note:
   299                              <1> 	; ebx, ecx, edx, edi, ebp registers
   300                              <1> 	; must be saved by VBE functions and
   301                              <1> 	; eax register must be set
   302                              <1> 	; (according to VBE 3 standard)
   303                              <1> 	; before return from this interrupt
   304                              <1> 	; (every function must restore and set
   305                              <1> 	; registers except esp, esi, es, ds)
   306                              <1> 
   307 0000177F 803D[CB080000]02    <1> 	cmp	byte [vbe3], 2
   308 00001786 773D                <1> 	ja	short VESA_VBE3_PMI_CALL ; VBE3 video bios ('PMID')
   309                              <1> 	;je	short VBE_func_0  ; Bochs/Qemu/VirtualBox emulator
   310 00001788 7268                <1> 	jb	short VBE_unknown ; invalid ([vbe3] = 0)
   311                              <1> 
   312                              <1> 	;jmp	VESA_VBE3_PMI_CALL
   313                              <1> 
   314                              <1> VBE_func_0:	
   315                              <1> 	; Bochs/Plex86 VGAbios VBE extension
   316                              <1> 	; (TRDOS 386 v2.0.3 can use VBE graphics modes on emulators)
   317                              <1> 	; BOCHS/QEMU/VIRTUALBOX
   318                              <1>  
   319 0000178A 8A25[CC080000]      <1> 	mov	ah, [vbe2bios]
   320 00001790 80FCC0              <1> 	cmp	ah, 0C0h		
   321 00001793 725D                <1> 	jb	short VBE_unknown 	
   322 00001795 80FCC5              <1> 	cmp	ah, 0C5h
   323 00001798 7758                <1> 	ja	short VBE_unknown
   324                              <1> 
   325                              <1> 	; TRDOS 386 is running on BOCHS or QEMU
   326 0000179A B44F                <1> 	mov	ah, 4Fh
   327                              <1> VBE_func_1:
   328 0000179C 0FB6F0              <1> 	movzx	esi, al ; VESA VBE function number
   329 0000179F 66C1E602            <1> 	shl	si, 2 ; dword
   330 000017A3 6683FE10            <1> 	cmp	si, N1L
   331 000017A7 7349                <1> 	jnb	short VBE_unknown
   332                              <1> 	;sti
   333                              <1> 	
   334 000017A9 FF96[B5170000]      <1> 	call	dword [esi+N1] ; call VBE function
   335                              <1> 		
   336                              <1> 	;jmp	short VBE_bios_return
   337                              <1> 
   338                              <1> VBE_bios_return:
   339 000017AF FA                  <1> 	cli
   340 000017B0 5E                  <1> 	pop	esi ; ****
   341 000017B1 5D                  <1> 	pop	ebp ; *** ; 27/11/2020
   342 000017B2 07                  <1> 	pop	es  ; **
   343 000017B3 1F                  <1> 	pop	ds  ; *
   344 000017B4 CF                  <1> 	iretd
   345                              <1> 
   346                              <1> N1:
   347 000017B5 [F2170000]          <1> 	dd	vbe_biosfn_return_ctrl_info
   348 000017B9 [F2170000]          <1> 	dd	vbe_biosfn_return_mode_info
   349 000017BD [58360000]          <1> 	dd	vbe_biosfn_set_mode
   350 000017C1 [13370000]          <1> 	dd	vbe_biosfn_return_current_mode
   351                              <1> 	;dd	vbe_biosfn_restore_video_state
   352                              <1> 	;dd	vbe_biosfn_save_restore_state
   353                              <1> 	;dd	vbe_biosfn_display_window_ctrl
   354                              <1> 	;dd	vbe_biosfn_set_get_log_scanline
   355                              <1> 	;dd	vbe_biosfn_set_get_disp_start
   356                              <1> 	;dd	vbe_biosfn_set_get_dac_pal_frm
   357                              <1> 	;dd	vbe_biosfn_set_get_palette_data
   358                              <1> 	
   359                              <1> N1L	EQU	$ - N1
   360                              <1> 
   361                              <1> 
   362                              <1> VESA_VBE3_PMI_CALL: ; VESA VBE video bios (firmware) functions
   363                              <1> 		    ; by using VESA VBE3 Protected Mode Interface
   364                              <1> 	
   365                              <1> 	; 29/11/2020
   366                              <1> 	; 26/11/2020 - TRDOS 386 v2.0.3 video.s
   367                              <1> 
   368                              <1> 	; We are here because..
   369                              <1> 	; 'PMID' has been verified by TRDOS 386 v2.0.3 kernel.
   370                              <1> 	; (Otherwise bochs/plex86 compatible VBE functions and
   371                              <1> 	;  modes would be used on BOCHS/QEMU/VIRTUALBOX emulators
   372                              <1> 	;  or only standard/old VGA graphics modes would be used.)   	
   373                              <1> 
   374                              <1> 	; (TRDOS 386 v2.0.3 can use VESA VBE graphics modes if
   375                              <1> 	;  the video bios is full compatible with VBE3 standard) 
   376                              <1> 
   377                              <1> 	; 29/11/2020
   378                              <1> 
   379 000017C5 0FB6F0              <1> 	movzx	esi, al ; VESA VBE 3 function number
   380 000017C8 66C1E602            <1> 	shl	si, 2 ; dword
   381 000017CC 6683FE10            <1> 	cmp	si, P1L
   382 000017D0 7320                <1> 	jnb	short VBE_unknown
   383                              <1> 	;sti
   384                              <1> 
   385 000017D2 57                  <1> 	push	edi ; *****
   386                              <1> 		
   387 000017D3 FF96[DC170000]      <1> 	call	dword [esi+P1] ; call VBE 3 function
   388                              <1> 
   389 000017D9 5F                  <1> 	pop	edi ; *****
   390                              <1> 		
   391 000017DA EBD3                <1> 	jmp	short VBE_bios_return
   392                              <1> 
   393                              <1> P1:
   394 000017DC [EC170000]          <1> 	dd	vbe3_pmfn_return_ctrl_info
   395 000017E0 [EC170000]          <1> 	dd	vbe3_pmfn_return_mode_info
   396 000017E4 [EC170000]          <1> 	dd	vbe3_pmfn_set_mode
   397 000017E8 [EC170000]          <1> 	dd	vbe3_pmfn_return_current_mode
   398                              <1> 	;dd	vbe3_pmfn_restore_video_state
   399                              <1> 	;dd	vbe3_pmfn_save_restore_state
   400                              <1> 	;dd	vbe3_pmfn_display_window_ctrl
   401                              <1> 	;dd	vbe3_pmfn_set_get_log_scanline
   402                              <1> 	;dd	vbe3_pmfn_set_get_disp_start
   403                              <1> 	;dd	vbe3_pmfn_set_get_dac_pal_frm
   404                              <1> 	;dd	vbe3_pmfn_set_get_palette_data
   405                              <1> 	;dd	vbe3_pmfn_return_pmi ; invalid for TRDOS 386 v2
   406                              <1> 	;dd	vbe3_pmfn_set_get_pixel_clock
   407                              <1> 	
   408                              <1> P1L	EQU	$ - P1
   409                              <1> 
   410                              <1> vbe3_pmfn_return_current_mode:
   411                              <1> 	; 30/11/2020
   412                              <1> vbe3_pmfn_set_mode:
   413                              <1> 	; 30/11/2020
   414                              <1> vbe3_pmfn_return_mode_info:
   415                              <1> 	; 30/11/2020
   416                              <1> vbe3_pmfn_return_ctrl_info:
   417                              <1> 
   418 000017EC 66B84F01            <1> 	mov	ax, 014Fh  ; ah = 1 : Function call failed	
   419                              <1> 			   ; al = 4Fh : Function is supported	
   420                              <1> 	
   421 000017F0 EBBD                <1> 	jmp	short VBE_bios_return
   422                              <1> 
   423                              <1> 
   424                              <1> ;	; 29/11/2020
   425                              <1> ;	mov	edi, VBE3MODEINFOBLOCK >> 4 ; / 16
   426                              <1> ;	
   427                              <1> ;	cmp	al, 04h
   428                              <1> ;	jb	short vbe3_pm_f ; function: 4F00h to 4F03h
   429                              <1> ;	ja	short vbe3_pmi_f5B ; function: 4F05h to 4F0Bh
   430                              <1> ;
   431                              <1> ;	; check buffer length (must be <= 2048 bytes)
   432                              <1> ;
   433                              <1> ;	and	dl, dl ; 0
   434                              <1> ;	jz	short vbe3_pm_f 
   435                              <1> ;		       ; Return Save/Restore State buffer size
   436                              <1> ;
   437                              <1> ;	push	ebx  ; buffer address
   438                              <1> ;	push	edx  ; function: save (01h) or restore (02h)
   439                              <1> ;	call	
   440                              <1> ;
   441                              <1> ;vbe3_pm_f03:
   442                              <1> ;	cmp	al, 2
   443                              <1> ;	ja	short vbe3_pm_f ; function 4F03h
   444                              <1> ;	jb	short vbe3_pm_f1
   445                              <1> ;
   446                              <1> ;
   447                              <1> ;vbe3_pm_f1:
   448                              <1> ;	
   449                              <1> ;
   450                              <1> ;vbe3_pmi_f5B:
   451                              <1> ;	cmp	al, 09h
   452                              <1> ;	jna	short vbe3_pm_f ; funcs 05h to 09h are usable 
   453                              <1> ;	
   454                              <1> ;	cmp	al, 0Bh ; Get/Set pixel clock, last function
   455                              <1> ;	jne	short VBE_unknown 
   456                              <1> ;			; (do not use 'uncertain' functions
   457                              <1> ;			; because of system-user buff transfers) 	
   458                              <1> ;vbe3_pm_f:
   459                              <1> ;	mov	byte [vbe3_pm_fn], al	; set
   460                              <1> ;	; prepare 16 bit pm segments & registers for pmi call 
   461                              <1> ;	call	VESA_VBE3_PM_FUNCTION
   462                              <1> ;
   463                              <1> ;
   464                              <1> 
   465                              <1> vbe_biosfn_return_ctrl_info: ; temporary
   466                              <1> vbe_biosfn_return_mode_info: ; temporary
   467                              <1> 	; 26/11/2020
   468                              <1> VBE_unknown:
   469 000017F2 66B80001            <1> 	mov	ax, 0100h  ; ah = 1 : Function call failed	
   470                              <1> 			   ; al = 0 : Function is not supported	
   471                              <1> 	
   472 000017F6 EBB7                <1> 	jmp	short VBE_bios_return
   473                              <1> 
   474                              <1> vesa_vbe3_pmi:
   475                              <1> 	; 28/11/2020
   476                              <1> 	; VGA BIOS functions via
   477                              <1> 	; VESA VBE3 Protected Mode Inface
   478                              <1> 	; [vbe3] = 3 and [pmi32] > 0
   479                              <1> 
   480 000017F8 20E4                <1> 	and	ah, ah ; 0 = set mode function
   481 000017FA 75C9                <1> 	jne	short VESA_VBE3_PMI_CALL
   482                              <1> 
   483 000017FC 3C13                <1> 	cmp	al, 13h ; mode number above 13h is returned
   484 000017FE 7605                <1> 	jna	short vbe3_pmi_1
   485                              <1> 			; back to default code due to uncertainty
   486                              <1> 	 		; (>13h is not std for all svga bioses)
   487 00001800 E95BFFFFFF          <1> 	jmp	vbe3_pmi_0
   488                              <1> vbe3_pmi_1:
   489 00001805 8825[176B0100]      <1> 	mov	byte [noclearmem], ah ; 0
   490                              <1> 	; check current video mode if it is 03h
   491 0000180B 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3
   492 00001812 7545                <1> 	jne	short vbe3_pmi_3
   493                              <1> 	; check new video mode if it is 03h also
   494 00001814 3C03                <1> 	cmp	al, 3
   495 00001816 7509                <1> 	jne	short vbe3_pmi_2
   496 00001818 C605[156B0100]80    <1> 	mov	byte [p_crt_mode], 80h 	; clear video memory
   497 0000181F EB43                <1> 	jmp	short vbe3_pmi_5
   498                              <1> vbe3_pmi_2:
   499                              <1> 	; case 1:
   500                              <1> 	; Current mode is 03h and new mode is not 03h
   501                              <1> 
   502                              <1> 	; save video pages and cursor positions
   503 00001821 56                  <1> 	push	esi
   504 00001822 57                  <1> 	push	edi
   505 00001823 51                  <1> 	push	ecx
   506 00001824 BE00800B00          <1> 	mov	esi, 0B8000h ; mode 3 video memory
   507 00001829 BF00800900          <1> 	mov	edi, 98000h  ; backup location
   508 0000182E B900200000          <1> 	mov	ecx, (0B8000h-0B0000h)/4
   509 00001833 F3A5                <1> 	rep	movsd
   510                              <1> 
   511 00001835 C605[156B0100]03    <1> 	mov	byte [p_crt_mode], 3 ; previous mode, backup sign
   512 0000183C 860D[AE5E0100]      <1> 	xchg	cl, [ACTIVE_PAGE]
   513 00001842 880D[166B0100]      <1> 	mov	[p_crt_page], cl  ; save as previous active page	
   514                              <1> 
   515                              <1> 	; save cursor positions
   516 00001848 BE[9E5E0100]        <1> 	mov	esi, CURSOR_POSN
   517 0000184D BF[1A6B0100]        <1> 	mov	edi, cursor_pposn ; cursor positions backup
   518 00001852 B104                <1> 	mov	cl, 4
   519 00001854 F3A5                <1> 	rep	movsd
   520                              <1> 
   521 00001856 59                  <1> 	pop	ecx
   522 00001857 5F                  <1> 	pop	edi
   523 00001858 5E                  <1> 	pop	esi
   524                              <1> vbe3_pmi_3:
   525 00001859 3C03                <1> 	cmp	al, 3
   526 0000185B 7407                <1> 	je	short vbe3_pmi_4
   527                              <1> 	; case 4:
   528                              <1> 	; Current mode is not 03h and also new mode is not 03h
   529 0000185D 800D[156B0100]80    <1> 	or	byte [p_crt_mode], 80h  ; 83h (case 1 -> case 4)
   530                              <1> vbe3_pmi_4:
   531                              <1> 	; case 3:
   532                              <1> 	;
   533                              <1> 	; Current mode is not 03h and new mode is 03h
   534                              <1> vbe3_pmi_5:
   535 00001864 A2[7A660000]        <1> 	mov	[CRT_MODE], al
   536                              <1> 
   537 00001869 E898000000          <1> 	call	int10h_32bit_pmi	
   538                              <1> 
   539 0000186E 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3  ; new video mode
   540 00001875 0F8588000000        <1> 	jne	vbe3_pmi_8	; video mode <> 03h
   541                              <1> 
   542 0000187B 50                  <1> 	push	eax
   543 0000187C 53                  <1> 	push	ebx
   544 0000187D 51                  <1> 	push	ecx
   545 0000187E 52                  <1> 	push	edx
   546 0000187F 5F                  <1> 	pop	edi
   547                              <1> 
   548 00001880 A0[166B0100]        <1> 	mov	al, [p_crt_page] ; previous mode 3 active page
   549                              <1> 
   550 00001885 F605[156B0100]7F    <1> 	test    byte [p_crt_mode], 7Fh ; 83h or 80h or 03h
   551 0000188C 7458                <1> 	jz	short vbe3_pmi_6 ; do not restore video pages
   552                              <1> 				 ; clear current video page
   553                              <1> 	; case 3
   554                              <1> 
   555                              <1> 	; ([p_crt_mode] = 03h)
   556                              <1> 
   557                              <1> 	; New video mode is 3 while current video mode is not 3
   558                              <1> 	; (multi screen) video pages will be restored from 098000h
   559                              <1> 
   560                              <1> 	; restore video pages and cursor positions
   561                              <1> 
   562 0000188E A2[AE5E0100]        <1> 	mov	[ACTIVE_PAGE], al ; current mode 3 active page
   563                              <1> 
   564 00001893 56                  <1> 	push	esi
   565                              <1> 
   566                              <1> 	; restore video pages
   567 00001894 BE00800900          <1> 	mov	esi, 98000h
   568 00001899 BF00800B00          <1> 	mov	edi, 0B8000h
   569 0000189E 66B90020            <1> 	mov	cx, 2000h ; 8K dwords (32K)
   570 000018A2 F3A5                <1> 	rep	movsd
   571                              <1> 
   572 000018A4 880D[156B0100]      <1> 	mov	[p_crt_mode], cl ; reset ('case 3' end condition)
   573                              <1> 
   574                              <1> 	; restore cursor positions
   575 000018AA BE[1A6B0100]        <1> 	mov	esi, cursor_pposn
   576 000018AF BF[9E5E0100]        <1> 	mov	edi, CURSOR_POSN
   577                              <1> 	;mov	ecx, 4	; restore all cursor positions (16 bytes)
   578 000018B4 B104                <1> 	mov	cl, 4
   579 000018B6 F3A5                <1> 	rep 	movsd
   580                              <1> 
   581 000018B8 5E                  <1> 	pop	esi
   582                              <1> 
   583                              <1> 	; check active page and set it again if it is not 0
   584 000018B9 08C0                <1> 	or	al, al
   585 000018BB 7441                <1> 	jz	short vbe3_pmi_7
   586                              <1> 
   587 000018BD B405                <1> 	mov	ah, 05h ; set current video page
   588                              <1> 	;al = video page
   589 000018BF E842000000          <1> 	call	int10h_32bit_pmi
   590                              <1> 
   591                              <1> 	; check current cursor position & set it again if not 0,0
   592 000018C4 0FB61D[AE5E0100]    <1> 	movzx	ebx, byte [ACTIVE_PAGE]
   593 000018CB D0E3                <1> 	shl	bl, 1
   594 000018CD 81C3[9E5E0100]      <1> 	add	ebx, CURSOR_POSN
   595 000018D3 668B13              <1> 	mov	dx, [ebx]
   596 000018D6 6621D2              <1> 	and	dx, dx		
   597 000018D9 7423                <1> 	jz	short vbe3_pmi_7
   598                              <1> 
   599 000018DB B705                <1> 	mov	bh, 05h
   600                              <1> 	;dx = cursor position (dl = column, dh = row)
   601 000018DD B402                <1> 	mov	ah, 02h ; set cursor position
   602 000018DF E822000000          <1> 	call	int10h_32bit_pmi
   603 000018E4 EB18                <1> 	jmp	short vbe3_pmi_7
   604                              <1> vbe3_pmi_6:
   605                              <1> 	; clear video page
   606 000018E6 B900040000          <1> 	mov	ecx, 1024 ; 4096/4
   607 000018EB B820072007          <1> 	mov	eax, 07200720h
   608 000018F0 BF00800B00          <1> 	mov	edi, 0B8000h ; [crt_base]
   609 000018F5 66033D[9C5E0100]    <1> 	add	di, [CRT_START]
   610 000018FC F3AB                <1> 	rep	stosd	; FILL THE REGEN BUFFER WITH BLANKS
   611                              <1> vbe3_pmi_7:
   612 000018FE 5F                  <1> 	pop	edi
   613 000018FF 5A                  <1> 	pop	edx
   614 00001900 59                  <1> 	pop	ecx
   615 00001901 5B                  <1> 	pop	ebx
   616 00001902 58                  <1> 	pop	eax
   617                              <1> vbe3_pmi_8:
   618                              <1> vesa_vbe3_pmi_retn:
   619 00001903 07                  <1> 	pop	es  ; **
   620 00001904 1F                  <1> 	pop	ds  ; *
   621 00001905 CF                  <1> 	iretd 
   622                              <1> 
   623                              <1> int10h_32bit_pmi:
   624                              <1> 	; 28/11/2020
   625                              <1> 	; calling standard VGA Bios (INT 10h) functions
   626                              <1> 	; by using 32 bit protected mode interface of
   627                              <1> 	; VESA VBE3 Video Bios (with 'PMID' signature)
   628                              <1> 
   629                              <1> 	; Temporary - 28/11/2020
   630                              <1> 	; Here, protected mode segment selectors, data and buffer
   631                              <1> 	; address must be prepared.. 
   632                              <1> 	; .. according to VESA VBE 3 standard	
   633                              <1> 	
   634 00001906 C3                  <1> 	retn
   635                              <1> 
   636                              <1> VIDEO_STATE:
   637                              <1> 	; 26/06/2016
   638                              <1> 	; 12/05/2016
   639                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
   640                              <1> 
   641                              <1> ;---------------------------------------------------
   642                              <1> ; VIDEO STATE
   643                              <1> ;  RETURNS THE CURRENT VIDEO STATE IN AX
   644                              <1> ;  AH = NUMBER OF COLUMNS ON THE SCREEN
   645                              <1> ;  AL = CURRENT VIDEO MODE
   646                              <1> ;  BH = CURRENT ACTIVE PAGE
   647                              <1> ;---------------------------------------------------
   648                              <1> 
   649 00001907 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS]	; GET NUMBER OF COLUMNS
   650 0000190D A0[7A660000]        <1> 	mov	al, [CRT_MODE]	; CURRENT MODE
   651                              <1> 	;movzx	esi, al
   652                              <1> 	;mov	ah, [esi+M6] 
   653                              <1> 	; BH = active page
   654 00001912 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE] ; GET CURRENT ACTIVE PAGE
   655 00001918 FA                  <1> 	cli	; 02/01/2017
   656 00001919 5D                  <1> 	pop	ebp		; RECOVER REGISTERS
   657 0000191A 5F                  <1> 	pop	edi
   658 0000191B 5E                  <1> 	pop	esi
   659 0000191C 59                  <1> 	pop	ecx		; DISCARD SAVED BX
   660 0000191D EB41                <1> 	jmp	short M15	; RETURN TO CALLER
   661                              <1> 
   662                              <1> set_mode_ncm:
   663                              <1> 	; 17/11/2020 (TRDOS 386 v2.0.3)
   664                              <1> 	; 04/07/2016 - TRDOS 386 (TRDOS v2.0)
   665                              <1> 	; set mode without clearing the video memory
   666                              <1> 	; (ony for graphics modes)
   667                              <1> 
   668                              <1> 	;cmp	al, 7 ; IBM PC CGA modes
   669                              <1> 	;jna	short SET_MODE ; normal function (clear)
   670                              <1> 	;; do not clear memory
   671                              <1> 	;;mov	[noclearmem], al ; > 0
   672                              <1> 	;mov	byte [noclearmem], 80h ; 17/11/2020
   673                              <1> 	;call	_set_mode
   674                              <1> 	;mov	byte [noclearmem], 0
   675                              <1>         ;jmp     short VIDEO_RETURN
   676                              <1> 
   677                              <1> 	; 17/11/2020 (TRDOS v2.0.3)
   678 0000191F 0C80                <1> 	or	al, 80h ; not clear memory option
   679                              <1> 
   680                              <1> 	; 27/11/2020
   681                              <1> 	; 17/11/2020
   682                              <1> 	; 10/08/2016
   683                              <1> 	; 08/08/2016
   684                              <1> 	; 29/07/2016, 30/07/2016
   685                              <1> 	; 25/07/2016, 26/07/2016, 27/07/2016
   686                              <1> 	; 02/07/2016, 18/07/2016, 23/07/2016
   687                              <1> 	; 24/06/2016, 26/06/2016
   688                              <1> 	; 29/05/2016 - TRDOS 386 (TRDOS v2.0)
   689                              <1> SET_MODE:
   690                              <1> 	; For 32 bit TRDOS and Retro UNIX 386:
   691                              <1> 	;	valid video mode: 03h only!
   692                              <1> 	;	(VGA modes will be selected with another routine)
   693                              <1> 	;
   694                              <1> 	; set_txt_mode ; 80*25 (16 fore colors, 8 back colors)
   695                              <1> 
   696                              <1> 	; 27/11/2020
   697                              <1> 	
   698                              <1> 	; Check if current mode is 
   699                              <1> 	; Bochs/Plex86 VBE graphics mode
   700 00001921 803D[7A660000]FF    <1> 	cmp	byte [CRT_MODE], 0FFh ; VESA VBE graphics mode
   701 00001928 7220                <1> 	jb	short _set_mode_      ; signature  	
   702                              <1> 				      ; VBE mode number is in	 
   703                              <1> 				      ; [video_mode] bit 0to8
   704 0000192A 88C3                <1> 	mov	bl, al ; save video mode
   705 0000192C E82F1E0000          <1> 	call	dispi_get_enable
   706 00001931 50                  <1> 	push	eax ; save current VBE dispi status 
   707                              <1> 	; Disable Bochs/Plex86 VBE dispi
   708                              <1> 	;mov	ax, 0 ; VBE_DISPI_DISABLED 
   709 00001932 31C0                <1> 	xor	eax, eax ; 0 
   710 00001934 E8FB1D0000          <1> 	call	dispi_set_enable
   711 00001939 88D8                <1> 	mov	al, bl ; restore video mode
   712 0000193B E827000000          <1> 	call	_set_mode
   713 00001940 58                  <1> 	pop	eax ; restore current VBE dispi status 
   714 00001941 7313                <1> 	jnc	short VIDEO_RETURN
   715                              <1> 	; ! unimplemented or invalid video mode number !
   716                              <1> 	; VBE dispi must be enabled again
   717                              <1> 	; (return to run on current VBE graphics mode)
   718                              <1> 	;;mov	al, [video_mode+1] ; bit 8 to 15
   719                              <1> 	;;and	al, 0C0h ; isolate bit 14 and bit 15 
   720                              <1> 	;;or	al, 1 ; VBE_DISPI_ENABLED
   721 00001943 E8EC1D0000          <1> 	call	dispi_set_enable
   722 00001948 EB07                <1> 	jmp	short _video_func_err
   723                              <1> 
   724                              <1> _set_mode_:
   725                              <1> 	; VGA bios (non-VBE) 'setmode' procedure
   726                              <1> 
   727                              <1> 	; 26/11/2020 (TRDOS v2.0.3)
   728                              <1> 	
   729                              <1> ;------------------------------------------------------
   730                              <1> ; SET MODE					      :
   731                              <1> ;	THIS ROUTINE INITIALIZES THE ATTACHMENT TO    :
   732                              <1> ;	THE SELECTED MODE, THE SCREEN IS BLANKED.     :
   733                              <1> ; INPUT						      :
   734                              <1> ;	(AL) - MODE SELECTED (RANGE 0-7)	      :
   735                              <1> ; OUTPUT					      :
   736                              <1> ;	NONE					      :
   737                              <1> ;------------------------------------------------------
   738                              <1> 
   739 0000194A E818000000          <1> 	call	_set_mode ; 24/06/2016 (set_txt_mode)
   740                              <1> 	; 26/11/2020
   741 0000194F 7305                <1> 	jnc	short VIDEO_RETURN
   742                              <1> 
   743                              <1> 	; 26/11/2020
   744                              <1> _video_func_err:
   745 00001951 31C0                <1> 	xor	eax, eax ; function call failed
   746 00001953 48                  <1> 	dec	eax  ; 0FFFFFFFFh ; - 1	
   747 00001954 EB05                <1> 	jmp	short _video_return	
   748                              <1> 
   749                              <1> ; 12/05/2016
   750                              <1> ; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
   751                              <1> 
   752                              <1> ;-----	NORMAL RETURN FROM ALL VIDEO RETURNS
   753                              <1> 
   754                              <1> VIDEO_RETURN:
   755 00001956 A1[086B0100]        <1> 	mov	eax, [video_eax] ; 12/05/2016
   756                              <1> _video_return:
   757 0000195B FA                  <1> 	cli ; 02/01/2017
   758 0000195C 5D                  <1> 	pop	ebp ; ******** ; 26/11/2020
   759 0000195D 5F                  <1> 	pop	edi ; *******
   760 0000195E 5E                  <1> 	pop	esi ; ******
   761 0000195F 5B                  <1> 	pop	ebx ; *****
   762                              <1> M15:	; VIDEO_RETURN_C
   763                              <1> 	;;15/01/2017
   764                              <1> 	; 02/01/2017
   765                              <1> 	;;mov	byte [intflg], 0
   766                              <1> 	;
   767 00001960 59                  <1> 	pop	ecx ; **** ; 26/11/2020
   768 00001961 5A                  <1> 	pop	edx ; ***
   769 00001962 1F                  <1> 	pop	ds  ; **
   770 00001963 07                  <1> 	pop	es  ; *	; RECOVER SEGMENTS
   771 00001964 CF                  <1> 	iretd		; ALL DONE
   772                              <1> 
   773                              <1> set_txt_mode:
   774                              <1> 	
   775                              <1> 	; 29/07/2016
   776                              <1> 	; 27/06/2016
   777 00001965 B003                <1> 	mov	al, 3 ; 26/11/2020 (bit 7 = 0)
   778                              <1> 
   779                              <1> 	; 17/11/2020 (TRDOS v2.0.3)
   780                              <1> 	;mov	byte [noclearmem], 0
   781                              <1> 
   782                              <1> ; 10/08/2016
   783                              <1> ; 08/08/2016
   784                              <1> ; 30/07/2016
   785                              <1> ; 29/07/2016
   786                              <1> ; 27/07/2016
   787                              <1> ; 26/07/2016
   788                              <1> ; 25/07/2016
   789                              <1> ; 23/07/2016
   790                              <1> ; 18/07/2016
   791                              <1> ; 07/07/2016
   792                              <1> ; 04/07/2016
   793                              <1> ; 03/07/2016
   794                              <1> ; 02/07/2016
   795                              <1> ; 26/06/2016
   796                              <1> ; 24/06/2016 (set_txt_mode -> _set_mode)
   797                              <1> ; 17/06/2016
   798                              <1> ; 29/05/2016
   799                              <1> ; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
   800                              <1> 
   801                              <1> _set_mode:
   802                              <1> 	; 26/11/2020
   803                              <1> 	; call from 'biosfn_set_video_mode'
   804                              <1> 	;	(bochs/plex86 video bios code)
   805                              <1> 	; call from 'SET_MODE'
   806                              <1> 	;	(TRDOS 386 v2 default, IBM PC/AT rom bios code)
   807                              <1> 	; continue from 'set_txt_mode'	
   808                              <1> 
   809                              <1> 	; INPUT:
   810                              <1> 	;	al = VGA video mode
   811                              <1> 	; RETURN:
   812                              <1> 	;	cf = 1 -> video mode not implemented
   813                              <1> 	;	cf = 0 -> OK
   814                              <1> 	;
   815                              <1> 	; Modified registers: eax, bx, ecx, esi, edi, (ebp)
   816                              <1> 
   817                              <1> 	; 17/11/2020 (TRDOS v2.0.3)
   818                              <1> 	; no clear memory option 
   819                              <1> 	; (from mode number byte bit 7)
   820 00001967 88C4                <1> 	mov	ah, al
   821 00001969 80E480              <1> 	and	ah, 80h
   822                              <1> 	;mov	[noclearmem], al
   823 0000196C 8825[176B0100]      <1> 	mov	[noclearmem], ah
   824                              <1> 	;and	al, 7Fh ; clear bit 7
   825                              <1> 	;;xor	[noclearmem], al ; clear bit 0 to 6
   826                              <1> 	; 26/11/2020
   827 00001972 30E0                <1> 	xor	al, ah ; and al, 7Fh
   828                              <1> 
   829                              <1> 	; 19/11/2020
   830                              <1> 
   831                              <1> 	; Video mode 03h action principle:
   832                              <1> 	;
   833                              <1> 	; for case 1:
   834                              <1> 	; Current mode is 03h and next/requested mode is not 03h
   835                              <1> 	;	- save mode (set mode 03h flag)
   836                              <1> 	;	- save 8 video pages (which are will be restored)	
   837                              <1> 	;	- save active page number (which will be reactivated)
   838                              <1> 	;	- set active page to 0 always (no multi screen)
   839                              <1> 	;	- save 8 cursor positions (which will be restored)
   840                              <1> 	; 	- use 'noclearmem' option
   841                              <1> 	;	[p_crt_mode] = 0 -> 03h 
   842                              <1> 	;
   843                              <1> 	; for case 2:
   844                              <1> 	; Current mode is 03h and next/requested mode is also 03h
   845                              <1> 	;	- clear active video page if 'noclearmem' is not set
   846                              <1> 	;	[p_crt_mode] = 0 -> 80h -> 0
   847                              <1> 	;
   848                              <1> 	; for case 3:
   849                              <1> 	; Current mode is not 03h and next/requested mode is 03h
   850                              <1> 	;	- restore video pages (8 video pages were saved)	
   851                              <1> 	;	- restore active page number (which were saved)
   852                              <1> 	;	- restore 8 cursor positions (which were saved)
   853                              <1> 	;	- reset/clear mode 03h flag
   854                              <1> 	;	[p_crt_mode] = 03h -> 0
   855                              <1> 	;
   856                              <1> 	; for case 4:
   857                              <1> 	; Current mode is not 03h and next/requested mode is not 03h
   858                              <1> 	; 	- use 'noclearmem' option
   859                              <1> 	;	- set active page to 0 always
   860                              <1> 	;	[p_crt_mode] = 03h -> 83h -> 03h
   861                              <1> 	;
   862                              <1> 	; initial (boot time) values:
   863                              <1> 	;	[p_crt_mode] = 0 ("there isn't a page backup, yet")
   864                              <1> 	;	  [CRT_MODE] = 3 (kernel's starting mode)
   865                              <1> 
   866                              <1> 	; 26/11/2020
   867 00001974 3C03                <1> 	cmp	al, 03h	    ; mode 3, 80x25 text, 16 colors
   868 00001976 7515                <1> 	jne	short _sm_0 ; (default mode for TRDOS 386 mainprog) 	
   869                              <1> 
   870                              <1> 	; case 2 or case 3
   871                              <1> 
   872                              <1> 	; check current video mode if it is 03h
   873 00001978 08E4                <1> 	or	ah, ah ; 80h or 0 ('noclearmem' option)
   874 0000197A 754D                <1> 	jnz	short _sm_1 ; do not clear display page
   875                              <1>  	
   876                              <1> 	; 26/11/2020
   877                              <1> 	; Note:
   878                              <1> 	; [CRT_MODE] = 0FFh for VESA VBE video modes
   879                              <1> 	; [video_mode] = standard VGA and VESA VBE video modes
   880                              <1> 	
   881 0000197C 3805[7A660000]      <1> 	cmp	[CRT_MODE], al	; 03h
   882 00001982 754C                <1> 	jne	short _sm_2	; case 3 ([p_crt_mode] = 03h)
   883                              <1> 
   884                              <1> 	; case 2
   885                              <1> 
   886                              <1> 	; [p_crt_mode] = 0
   887                              <1> 
   888                              <1> 	; 19/11/2020
   889                              <1> 	; If '_set_mode' procedure is called for video mode 3
   890                              <1> 	;     while video mode is 3, video page will be cleared
   891                              <1> 	;     and cursor position of video page will be reset.	 
   892                              <1> 
   893                              <1> 	; clear display page
   894 00001984 C605[156B0100]80    <1> 	mov	byte [p_crt_mode], 80h ; clear page sign
   895 0000198B EB48                <1> 	jmp	short _sm_3	; bypass save video page routine
   896                              <1> _sm_0:
   897                              <1> 	; case 1 or case 4
   898                              <1> 
   899 0000198D 3A05[7A660000]      <1> 	cmp	al, [CRT_MODE]	; is current mode 03h?
   900 00001993 7534                <1> 	jne	short _sm_1	; case 4 ; [p_crt_mode] = 03h
   901                              <1> 	
   902                              <1> 	; case 1
   903                              <1> 	; [p_crt_mode] = 0
   904                              <1> 
   905                              <1> 	; 19/11/2020
   906                              <1> 	; If '_set_mode' procedure is called for a video mode
   907                              <1> 	;     except video mode 3 while current video mode
   908                              <1> 	;     is 3, all video pages of mode 3 will be copied 
   909                              <1> 	;     to 98000h address as backup, before mode change.	
   910                              <1> 	
   911                              <1> _sm_save_pm:
   912                              <1> 	; 03/07/2016
   913                              <1> 	; save video pages
   914 00001995 BE00800B00          <1> 	mov	esi, 0B8000h
   915 0000199A BF00800900          <1> 	mov	edi, 98000h ; 30/07/2016
   916 0000199F B900200000          <1> 	mov	ecx, (0B8000h-0B0000h)/4
   917 000019A4 F3A5                <1> 	rep	movsd
   918                              <1> 
   919 000019A6 C605[156B0100]03    <1> 	mov	byte [p_crt_mode], 3 ; previous mode, backup sign
   920                              <1> 	; 26/11/2020
   921 000019AD 860D[AE5E0100]      <1> 	xchg	cl, [ACTIVE_PAGE]
   922 000019B3 880D[166B0100]      <1> 	mov	[p_crt_page], cl  ; save as previous active page	
   923                              <1> 
   924                              <1> 	; save cursor positions
   925 000019B9 BE[9E5E0100]        <1> 	mov	esi, CURSOR_POSN
   926 000019BE BF[1A6B0100]        <1> 	mov	edi, cursor_pposn ; cursor positions backup
   927 000019C3 B104                <1> 	mov	cl, 4
   928 000019C5 F3A5                <1> 	rep	movsd
   929                              <1> 
   930                              <1> 	; 29/07/2016
   931                              <1> 	;;mov	[ACTIVE_PAGE], cl ; 0
   932                              <1> 	;xchg	cl, [ACTIVE_PAGE]
   933                              <1> 	;mov	[p_crt_page], cl  ; previous page (for mode 3)	
   934                              <1> 	
   935                              <1> 	; [ACTIVE_PAGE] = 0 
   936                              <1> 	
   937 000019C7 EB07                <1> 	jmp	short _sm_2	; case 1 - 19/11/2020
   938                              <1> _sm_1:
   939                              <1> 	; 26/11/2020
   940                              <1> 	; 19/11/2020
   941                              <1> 	
   942                              <1> 	; case 4
   943 000019C9 800D[156B0100]80    <1> 	or	byte [p_crt_mode], 80h 
   944                              <1> 				; here [p_crt_mode] must be 83h
   945                              <1> 				;	  (for case 4)
   946                              <1> 				; (because video mode 03h
   947                              <1> 				; was changed before as in case 1) 
   948                              <1> 
   949                              <1> _sm_2:	; case 4 (jump to _sm_2) - 19/11/2020 
   950                              <1> 
   951                              <1> 	; 19/11/2020
   952                              <1> 	; case 3
   953                              <1> 	; If '_set_mode' procedure is called for video mode 3
   954                              <1> 	;     while video mode is not 3 and if there is video
   955                              <1> 	;     page backup for video mode 3, all (of 8) mode 3
   956                              <1> 	;     video pages will be restored from 98000h.
   957                              <1> 
   958 000019D0 A2[7A660000]        <1> 	mov	[CRT_MODE], al  ; save mode in global variable
   959                              <1> _sm_3:
   960                              <1> 	; 30/07/2016
   961                              <1> 	; 26/07/2016
   962                              <1> 	; 25/07/2016
   963                              <1> 	; set_mode_vga:
   964                              <1> 	; 18/07/2016
   965                              <1> 	; 14/07/2016
   966                              <1> 	; 09/07/2016
   967                              <1> 	; 04/07/2016
   968                              <1> 	; 03/07/2016 (TRDOS 386 = TRDOS v2.0)
   969                              <1> 	; /// video mode 13h ///
   970                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
   971                              <1> 	; vgabios-0.7a (2011)
   972                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
   973                              <1> 	; 'vgabios.c', 'vgatables.h'
   974                              <1> 	;
   975                              <1> 	; Oracle VirtualBox 5.0.24 VGABios Source Code
   976                              <1> 	; ('vgabios.c', 'vgatables.h', 'vgafonts.h', 'vgarom.asm')
   977                              <1> 	;
   978 000019D5 88C4                <1> 	mov	ah, al
   979 000019D7 B910000000          <1> 	mov	ecx, vga_mode_count 	
   980 000019DC BE[96660000]        <1> 	mov	esi, vga_modes
   981 000019E1 31DB                <1> 	xor	ebx, ebx
   982                              <1> _sm_4:
   983 000019E3 AC                  <1> 	lodsb
   984 000019E4 38C4                <1> 	cmp	ah, al
   985 000019E6 7406                <1> 	je	short _sm_5
   986 000019E8 FEC3                <1> 	inc	bl
   987 000019EA E2F7                <1> 	loop	_sm_4
   988                              <1> 
   989                              <1> 	; UNIMPLEMENTED VIDEO MODE !
   990                              <1> 	;xor	eax, eax
   991                              <1>         ;mov	[video_eax], eax ; 0 
   992                              <1> 
   993                              <1> 	; 26/11/2020
   994 000019EC F9                  <1> 	stc	; unimplemented video mode ! (cf=1)	
   995                              <1> 
   996 000019ED C3                  <1> 	retn
   997                              <1> 
   998                              <1> ;-----	eBX POINTS TO CORRECT ROW OF INITIALIZATION TABLE	
   999                              <1> 
  1000                              <1> _sm_5: 	; 25/07/2016
  1001                              <1> 	;mov	esi, ebx
  1002                              <1> 	;add	esi, vga_memmodel
  1003                              <1> 	;mov	al, [esi]
  1004                              <1> 	; 19/11/2020
  1005 000019EE 8A83[E6660000]      <1> 	mov	al, [ebx+vga_memmodel]
  1006 000019F4 A2[2E6B0100]        <1> 	mov	[VGA_MTYPE], al
  1007                              <1> 
  1008 000019F9 89DF                <1> 	mov	edi, ebx
  1009 000019FB 81C7[F6660000]      <1> 	add	edi, vga_dac_s 	
  1010 00001A01 C0E302              <1> 	shl	bl, 2 ; byte -> dword
  1011 00001A04 81C3[A6660000]      <1> 	add	ebx, vga_mode_tbl_ptr
  1012                              <1> 
  1013                              <1> 	;mov	dword [VGA_BASE], 0B8000h
  1014                              <1> 	;cmp	ah, 0Dh ; [CRT_MODE]
  1015                              <1> 	;jb	short M9 
  1016                              <1> 	;mov	dword [VGA_BASE], 0A0000h
  1017                              <1> ;M9:
  1018 00001A0A 8B33                <1> 	mov	esi, [ebx]
  1019 00001A0C 89F3                <1> 	mov	ebx, esi
  1020 00001A0E 83C614              <1> 	add	esi, vga_p_cm_pos ; ebx + 20
  1021 00001A11 668B06              <1> 	mov	ax, [esi]       ; get the cursor mode from the table
  1022 00001A14 66A3[93660000]      <1> 	mov	[CURSOR_MODE], ax ; save cursor mode (initial value)
  1023                              <1> 	; al = 6, ah = 7
  1024                              <1> 	; al = 0Dh, ah = 0Eh ; 25/07/2016
  1025 00001A1A E84C020000          <1> 	call	cursor_shape_fix
  1026                              <1> 	; al = 14, ah = 15 (If [CHAR_HEIGHT] = 16)
  1027 00001A1F 668906              <1> 	mov	[esi], ax
  1028                              <1> 
  1029 00001A22 56                  <1> 	push	esi ; *	
  1030                              <1> 
  1031 00001A23 8A25[81660000]      <1> 	mov	ah, [VGA_MODESET_CTL]
  1032 00001A29 80E408              <1> 	and	ah, 8 ; default palette loading ?
  1033 00001A2C 7524                <1> 	jnz	short _sm_6
  1034 00001A2E 66BAC603            <1> 	mov	dx, 3C6h ; VGAREG_PEL_MASK (DAC mask register)
  1035 00001A32 B0FF                <1> 	mov	al, 0FFh ; PEL mask
  1036 00001A34 EE                  <1> 	out	dx, al
  1037 00001A35 8A27                <1> 	mov	ah, [edi] ; DAC model (selection number)
  1038 00001A37 E829100000          <1> 	call	load_dac_palette
  1039                              <1> 	; ecx = 0
  1040 00001A3C F605[81660000]02    <1> 	test	byte [VGA_MODESET_CTL], 2 ; gray scale summing
  1041 00001A43 740D                <1> 	jz	short _sm_6
  1042 00001A45 53                  <1> 	push	ebx
  1043 00001A46 29DB                <1> 	sub	ebx, ebx ; sub bl, bl
  1044 00001A48 66B90001            <1>         mov     cx, 256 
  1045 00001A4C E867100000          <1> 	call	gray_scale_summing
  1046 00001A51 5B                  <1> 	pop	ebx	
  1047                              <1> _sm_6:
  1048                              <1> 	; Reset Attribute Ctl flip-flop
  1049 00001A52 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  1050 00001A56 EC                  <1>  	in	al, dx
  1051                              <1> 	; Set Attribute Ctl
  1052 00001A57 89DE                <1> 	mov	esi, ebx ; addr of params tbl for selected mode
  1053 00001A59 83C623              <1> 	add	esi, 35  ; actl regs
  1054 00001A5C 30E4                <1> 	xor	ah, ah ; 0
  1055 00001A5E 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  1056                              <1> _sm_7:
  1057 00001A62 88E0                <1> 	mov	al, ah
  1058 00001A64 EE                  <1> 	out	dx, al ; index
  1059 00001A65 AC                  <1> 	lodsb
  1060                              <1> 	; DX = 3C0h = VGAREG_ACTL_WRITE_DATA
  1061 00001A66 EE                  <1> 	out	dx, al ; value
  1062 00001A67 FEC4                <1> 	inc	ah
  1063 00001A69 80FC14              <1> 	cmp	ah, 20 ; number of actl registers
  1064 00001A6C 72F4                <1> 	jb	short _sm_7
  1065                              <1> 	;
  1066 00001A6E 88E0                <1> 	mov	al, ah ; 20
  1067 00001A70 EE                  <1> 	out	dx, al ; index
  1068 00001A71 28C0                <1> 	sub	al, al ; 0
  1069 00001A73 EE                  <1> 	out	dx, al ; value
  1070                              <1> 	;
  1071                              <1> 	; Set Sequencer Ctl
  1072 00001A74 89DE                <1> 	mov	esi, ebx ; addr of params tbl for selected mode
  1073 00001A76 83C605              <1> 	add	esi, 5 ; sequ regs
  1074                              <1> 	;
  1075 00001A79 66BAC403            <1> 	mov	dx, 3C4h  ; VGAREG_SEQU_ADDRESS
  1076 00001A7D EE                  <1> 	out	dx, al ; 0
  1077 00001A7E 6642                <1> 	inc	dx ; 3C5h ; VGAREG_SEQU_DATA
  1078 00001A80 B003                <1> 	mov	al, 3
  1079 00001A82 EE                  <1> 	out	dx, al
  1080 00001A83 B401                <1> 	mov	ah, 1	
  1081                              <1> _sm_8:
  1082 00001A85 88E0                <1> 	mov	al, ah
  1083                              <1> 	;mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  1084 00001A87 664A                <1> 	dec	dx
  1085 00001A89 EE                  <1> 	out	dx, al ; index
  1086 00001A8A AC                  <1> 	lodsb
  1087 00001A8B 6642                <1> 	inc	dx ; 3C5h ; VGAREG_SEQU_DATA
  1088 00001A8D EE                  <1> 	out	dx, al
  1089 00001A8E 80FC04              <1> 	cmp	ah, 4 ; number of sequ regs
  1090 00001A91 7304                <1> 	jnb	short _sm_9		
  1091 00001A93 FEC4                <1> 	inc	ah 
  1092 00001A95 EBEE                <1> 	jmp	short _sm_8
  1093                              <1> _sm_9:
  1094                              <1> 	; Set Grafx Ctl
  1095 00001A97 89DE                <1> 	mov	esi, ebx ; addr of params tbl for selected mode
  1096 00001A99 83C637              <1> 	add	esi, 55 ; grdc regs
  1097 00001A9C 30E4                <1> 	xor	ah, ah ; 0
  1098                              <1> _sm_10:
  1099 00001A9E 88E0                <1> 	mov	al, ah
  1100 00001AA0 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  1101 00001AA4 EE                  <1> 	out	dx, al	
  1102 00001AA5 AC                  <1> 	lodsb
  1103 00001AA6 6642                <1> 	inc	dx ; 3CFh ; VGAREG_GRDC_DATA
  1104 00001AA8 EE                  <1> 	out	dx, al
  1105 00001AA9 FEC4                <1> 	inc	ah
  1106 00001AAB 80FC09              <1> 	cmp	ah, 9 ; number of grdc regs
  1107 00001AAE 72EE                <1> 	jb	short _sm_10
  1108                              <1> 	;
  1109                              <1> 	; Disable CRTC write protection
  1110 00001AB0 66BAD403            <1> 	mov	dx, 3D4h  ; VGAREG_VGA_CRTC_ADDRESS
  1111                              <1> 	;mov	al, 11h
  1112                              <1> 	;our	dx, al
  1113                              <1> 	;inc	dx
  1114                              <1> 	;sub	al, al
  1115                              <1> 	;out	dx, al
  1116 00001AB4 66B81100            <1> 	mov	ax, 11h
  1117 00001AB8 66EF                <1> 	out	dx, ax
  1118 00001ABA 89DE                <1> 	mov	esi, ebx ; addr of params tbl for selected mode
  1119 00001ABC 83C60A              <1> 	add	esi, 10 ; crtc regs
  1120                              <1> 	; ah = 0
  1121                              <1> _sm_11:
  1122 00001ABF 88E0                <1> 	mov	al, ah
  1123                              <1> 	; dx = 3D4h = VGAREG_VGA_CRTC_ADDRESS
  1124 00001AC1 EE                  <1> 	out	dx, al ; index
  1125 00001AC2 AC                  <1> 	lodsb
  1126 00001AC3 6642                <1> 	inc	dx  ; VGAREG_VGA_CRTC_ADDRESS + 1
  1127 00001AC5 EE                  <1> 	out	dx, al ; value
  1128 00001AC6 80FC18              <1> 	cmp	ah, 24 ; number of crtc registers - 1
  1129 00001AC9 7306                <1> 	jnb	short _sm_12
  1130 00001ACB FEC4                <1> 	inc	ah
  1131 00001ACD 664A                <1> 	dec	dx ; 3D4h
  1132 00001ACF EBEE                <1> 	jmp	short _sm_11
  1133                              <1> _sm_12:
  1134                              <1> 	; Set the misc register
  1135 00001AD1 66BACC03            <1> 	mov	dx, 3CCh ; VGAREG_READ_MISC_OUTPUT
  1136 00001AD5 8A4309              <1> 	mov	al, [ebx+9] ; misc reg
  1137 00001AD8 EE                  <1> 	out	dx, al
  1138                              <1> 	;
  1139                              <1> 	; Enable video
  1140 00001AD9 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  1141 00001ADD B020                <1> 	mov	al, 20h  
  1142 00001ADF EE                  <1>         out     dx, al   ; set bit 5 to 1
  1143 00001AE0 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  1144 00001AE4 EC                  <1> 	in	al, dx
  1145                              <1> 	;
  1146                              <1> 	; 17/11/2020
  1147                              <1> 	;cmp	byte [noclearmem], 0
  1148                              <1>         ;ja	short _sm_15
  1149                              <1> 
  1150 00001AE5 F605[176B0100]80    <1> 	test	byte [noclearmem], 80h
  1151 00001AEC 7540                <1> 	jnz	short _sm_15	
  1152                              <1> 
  1153                              <1> 	; 29/07/2016
  1154 00001AEE 31C0                <1> 	xor	eax, eax
  1155 00001AF0 B900400000          <1> 	mov	ecx, 4000h ; 16K words (32K)
  1156 00001AF5 803D[2E6B0100]02    <1> 	cmp     byte [VGA_MTYPE], 2  ; CTEXT, MTEXT, CGA
  1157 00001AFC 7715                <1> 	ja	short _sm_14    ; no ? (0A0000h)
  1158 00001AFE BF00800B00          <1> 	mov	edi, 0B8000h
  1159 00001B03 7409                <1> 	je	short _sm_13	; CGA graphics mode
  1160                              <1> 	; 08/08/2016
  1161 00001B05 A3[2A6B0100]        <1> 	mov	[VGA_INT43H], eax ; 0 ; default font 
  1162 00001B0A 66B82007            <1> 	mov	ax, 0720h	; CGA text mode
  1163                              <1> _sm_13:
  1164 00001B0E F366AB              <1> 	rep	stosw
  1165 00001B11 EB1B                <1> 	jmp	short _sm_15		
  1166                              <1> 
  1167                              <1> _sm_14:
  1168 00001B13 BF00000A00          <1> 	mov	edi, 0A0000h
  1169                              <1> 	; ecx = 16384 dwords (64K)
  1170 00001B18 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  1171 00001B1C B002                <1> 	mov	al, 2
  1172 00001B1E EE                  <1> 	out	dx, al
  1173                              <1> 	;mov	dx, 3C5h ; VGAREG_SEQU_DATA
  1174 00001B1F 6642                <1> 	inc	dx
  1175 00001B21 EC                  <1> 	in	al, dx ; mmask
  1176 00001B22 6650                <1> 	push	ax
  1177 00001B24 B00F                <1> 	mov	al, 0Fh ; all planes
  1178 00001B26 EE                  <1> 	out	dx, al
  1179 00001B27 30C0                <1> 	xor	al, al ; 0
  1180 00001B29 F3AB                <1> 	rep	stosd	; ecx = 163684 (64K)
  1181 00001B2B 6658                <1> 	pop	ax
  1182 00001B2D EE                  <1> 	out	dx, al  ; mmask
  1183                              <1> _sm_15:
  1184                              <1> 	; ebx = addr of params tbl for selected mode
  1185                              <1> 	; 10/08/2016
  1186 00001B2E 668B03              <1> 	mov	ax, [ebx] ; num of columns, 'twidth'
  1187 00001B31 A2[7C660000]        <1> 	mov	[CRT_COLS], al
  1188                              <1> 	;; 26/07/2016
  1189                              <1> 	;; CRTC_ADDRESS = 3D4h (always)
  1190                              <1> 	;mov	ah, [ebx+1] ; num of rows, 'theightm1'
  1191 00001B36 FEC4                <1> 	inc	ah ; 09/07/2016
  1192 00001B38 8825[82660000]      <1> 	mov	[VGA_ROWS], ah
  1193                              <1> 	; 10/08/2016
  1194 00001B3E 8A4302              <1> 	mov	al, [ebx+2]
  1195 00001B41 A2[7E660000]        <1> 	mov	[CHAR_HEIGHT], al 
  1196                              <1> 	; 29/07/2016
  1197                              <1> 	; length of regen buffer in bytes
  1198 00001B46 668B4B03            <1> 	mov	cx, [ebx+3] ; 'slength_l'
  1199 00001B4A 66890D[186B0100]    <1> 	mov	[CRT_LEN], cx
  1200                              <1> 	;
  1201                              <1> 	; 27/07/2016
  1202 00001B51 30E4                <1> 	xor	ah, ah
  1203 00001B53 A0[AE5E0100]        <1> 	mov	al, [ACTIVE_PAGE] ; may be > 0 for mode 3
  1204                              <1> 	;mul	word [CRT_LEN] ; 4096 for mode 3
  1205 00001B58 66F7E1              <1> 	mul	cx ; 29/07/2016
  1206 00001B5B 66A3[9C5E0100]      <1> 	mov	[CRT_START], ax
  1207                              <1> 	;
  1208 00001B61 B060                <1> 	mov	al, 60h
  1209                              <1> 	;cmp	byte [noclearmem], 0
  1210                              <1> 	;jna	short _sm_16
  1211                              <1> 	;add	al, 80h
  1212 00001B63 0A05[176B0100]      <1> 	or	al, [noclearmem] ; 17/11/2020
  1213                              <1> _sm_16:
  1214 00001B69 A2[7F660000]        <1> 	mov	[VGA_VIDEO_CTL], al
  1215 00001B6E C605[80660000]F9    <1> 	mov	byte [VGA_SWITCHES], 0F9h
  1216 00001B75 8025[81660000]7F    <1> 	and	byte [VGA_MODESET_CTL], 7Fh
  1217                              <1> 
  1218 00001B7C 5E                  <1> 	pop	esi ; *
  1219                              <1> 
  1220                              <1> 	; 26/07/2016
  1221                              <1> 	; 07/07/2016
  1222 00001B7D 668B0D[93660000]    <1> 	mov	cx, [CURSOR_MODE] ; restore cursor mode (initial value)
  1223 00001B84 66870E              <1> 	xchg	cx, [esi] ; cl = start line, ch = end line
  1224                              <1> 			  ; reset to initial value
  1225 00001B87 86E9                <1> 	xchg 	ch, cl  ; ch = start line, cl = end line  
  1226 00001B89 66890D[93660000]    <1> 	mov	[CURSOR_MODE], cx ; save (fixed) cursor mode
  1227                              <1> 
  1228                              <1> 	; 27/07/2016
  1229 00001B90 803D[2E6B0100]02    <1> 	cmp	byte [VGA_MTYPE], 2 ; CTEXT, MTEXT
  1230 00001B97 7317                <1> 	jnb	short _sm_17
  1231                              <1> 
  1232                              <1> 	; Set cursor shape
  1233                              <1> 	;mov	cx, 0607h
  1234                              <1> 	;call	_set_ctype
  1235                              <1> 
  1236                              <1> 	; 29/07/2016
  1237 00001B99 B40A                <1> 	mov	ah, 10	; 6845 register for cursor set
  1238 00001B9B E8FE050000          <1> 	call	m16	; output cx register
  1239                              <1> 	
  1240                              <1> 	; 25/07/2016
  1241 00001BA0 803D[7A660000]03    <1>         cmp     byte [CRT_MODE], 03h
  1242 00001BA7 7507                <1> 	jne	short _sm_17
  1243                              <1> 	; 26/07/2016
  1244                              <1> 
  1245 00001BA9 A0[AE5E0100]        <1> 	mov	al, [ACTIVE_PAGE]
  1246 00001BAE EB0B                <1> 	jmp	short _sm_18
  1247                              <1> _sm_17:
  1248                              <1> 	; Set cursor pos for page 0..7
  1249                              <1> 	;sub	ax, ax ; eax = 0
  1250 00001BB0 29C0                <1> 	sub	eax, eax ; 17/11/2020
  1251 00001BB2 BF[9E5E0100]        <1> 	mov	edi, CURSOR_POSN
  1252 00001BB7 AB                  <1> 	stosd	
  1253 00001BB8 AB                  <1> 	stosd
  1254 00001BB9 AB                  <1> 	stosd
  1255 00001BBA AB                  <1> 	stosd
  1256                              <1> 	;; Set active page 0
  1257                              <1> 	;mov	[ACTIVE_PAGE], al ; 0
  1258                              <1> _sm_18:
  1259                              <1> 	; 29/07/2016
  1260 00001BBB 803D[2E6B0100]02    <1> 	cmp	byte [VGA_MTYPE], 2 ; CTEXT, MTEXT
  1261 00001BC2 0F839E000000        <1>         jnb	_sm_23
  1262                              <1> 
  1263                              <1> 	;cmp	byte [CHAR_HEIGHT], 16
  1264                              <1> 	;je	short _sm_19
  1265                              <1> 
  1266                              <1>  	;; copy and activate 8x16 font
  1267                              <1> 	
  1268                              <1> 	; 26/07/2016
  1269 00001BC8 B004                <1> 	mov	al, 04h
  1270                              <1> 	;sub	bl, bl
  1271                              <1> 	; AX = 1104H ; Load ROM 8x16 Character Set
  1272                              <1> 	; (BL = font block to load (EGA: 0-3; VGA: 0-7))
  1273 00001BCA E87A150000          <1> 	call	load_text_8_16_pat
  1274                              <1> 
  1275                              <1> 	; video_func_1103h:
  1276                              <1> 	; biosfn_set_text_block_specifier:
  1277                              <1> 	; BL = font block selector code	
  1278                              <1> 	; NOTE: TRDOS 386 only uses and sets font block 0
  1279                              <1> 	; (It is as BL = 0 for TRDOS 386)
  1280 00001BCF 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  1281                              <1> 	;;mov	ah, bl
  1282                              <1> 	;sub	ah, ah ; 0
  1283                              <1> 	;mov	al, 03h
  1284                              <1> 	; 19/11/2020
  1285 00001BD3 66B80300            <1> 	mov	ax, 03h
  1286 00001BD7 66EF                <1> 	out	dx, ax
  1287                              <1> _sm_19:
  1288                              <1> 	; 29/07/2016
  1289                              <1> 	; 26/07/2016
  1290                              <1> 	; 24/06/2016
  1291                              <1> 	;mov	edi, 0B8000h
  1292                              <1> 	;mov	cx, 4000h ; 16K words (32K)
  1293                              <1> 	;
  1294 00001BD9 30C0                <1> 	xor	al, al
  1295 00001BDB 3805[156B0100]      <1>         cmp     [p_crt_mode], al ; 0 
  1296 00001BE1 7705                <1>         ja      short _sm_20 ; 03h, 80h or 83h
  1297                              <1> 
  1298                              <1> 	; case 1 - 19/11/2020
  1299                              <1> 	;
  1300                              <1> 	; If [pc_crt_mode] = 0, that means, previous mode is 03h
  1301                              <1> 	; and current mode is not 03h (case 1)
  1302                              <1> 
  1303                              <1> 	; 30/07/2016
  1304                              <1> 	; 24/06/2016
  1305                              <1> 	; TRDOS 386 (TRDOS v2) 'set mode' modification
  1306                              <1> 	; (for multiscreen feature):
  1307                              <1> 	; If '_set_mode' procedure is called for video mode 3
  1308                              <1> 	;     while video mode is 3, video page will be cleared
  1309                              <1> 	;     and cursor position of video page will be reset.	  
  1310                              <1> 	; If '_set_mode' procedure is called for a video mode
  1311                              <1> 	;     except video mode 3, while current video mode
  1312                              <1> 	;     is 3, all video pages of mode 3 will be copied 
  1313                              <1> 	;     to 98000h address as backup, before mode change.	 	
  1314                              <1> 	; If '_set_mode' procedure is called for video mode 3
  1315                              <1> 	;     while video mode is not 3 and if there is video
  1316                              <1> 	;     page backup for video mode 3, all (of 8) mode 3
  1317                              <1> 	;     video pages will be restored from 98000h.
  1318                              <1> 
  1319                              <1> 	; 19/11/2020
  1320                              <1> 	;mov	[ACTIVE_PAGE], al ; 0
  1321                              <1> 
  1322                              <1> 	; Here,
  1323                              <1> 	; video memory already cleared if [noclearmem] <> 80h
  1324                              <1> 	
  1325                              <1> 	;mov	ax, 0720h
  1326                              <1> 	;mov	cx, 4000h ; 16K words (32K)
  1327                              <1> 	;mov	edi, 0B8000h
  1328                              <1> 	;rep	stosw
  1329                              <1> 	;sub	al, al
  1330                              <1> 	
  1331                              <1> 	;jmp	short _sm_23
  1332                              <1> 
  1333                              <1> 	; Set hardware side for the new active video page
  1334                              <1>  
  1335 00001BE3 E99B010000          <1> 	jmp	_set_active_page ; 19/11/2020	
  1336                              <1> 
  1337                              <1> _sm_20:
  1338                              <1> 	; 19/11/2020
  1339                              <1> 	; case 2 or case 3 or case 4 - 19/11/2020
  1340                              <1> 	
  1341                              <1> 	; 19/11/2020
  1342 00001BE8 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3  ; new video mode
  1343 00001BEF 756E                <1> 	jne	short _sm_22 ; al = 0 (& video mode <> 03h)
  1344                              <1> 			     ; case 4 - 19/11/2020
  1345                              <1> 			     ; ([p_crt_mode] = 83h) 		
  1346                              <1> 
  1347                              <1> 	; case 2 or case 3 - 19/11/2020	
  1348                              <1> 
  1349                              <1> 	;movzx	ebx, byte [ACTIVE_PAGE]
  1350                              <1> 	; 19/11/2020
  1351 00001BF1 A0[166B0100]        <1> 	mov	al, [p_crt_page] ; previous mode 3 active page
  1352                              <1> 	;movzx	ebx, al
  1353                              <1> 	;shl	bl, 1 ; * 2
  1354                              <1> 	;add	ebx, CURSOR_POSN
  1355                              <1> 
  1356                              <1> 	; 29/07/2016
  1357 00001BF6 F605[156B0100]7F    <1> 	test    byte [p_crt_mode], 7Fh ; 83h or 80h or 03h
  1358 00001BFD 742E                <1> 	jz	short _sm_21	; do not restore video pages
  1359                              <1> 				; case 2 - 19/11/2020 
  1360                              <1> 	; case 3 - 19/11/2020
  1361                              <1> 
  1362                              <1> 	; ([p_crt_mode] = 03h)
  1363                              <1> 
  1364                              <1> 	; New video mode is 3 while current video mode is not 3
  1365                              <1> 	; (multi screen) video pages will be restored from 098000h
  1366                              <1> 
  1367                              <1> 	; 19/11/2020
  1368 00001BFF A2[AE5E0100]        <1> 	mov	[ACTIVE_PAGE], al ; current mode 3 active page
  1369                              <1> 
  1370                              <1> 	; restore video pages
  1371 00001C04 BE00800900          <1> 	mov	esi, 98000h ; 30/07/2016 
  1372 00001C09 BF00800B00          <1> 	mov	edi, 0B8000h
  1373 00001C0E 66B90020            <1> 	mov	cx, 2000h ; 8K dwords (32K)
  1374 00001C12 F3A5                <1> 	rep	movsd
  1375                              <1> 
  1376                              <1> 	; 19/11/2020
  1377 00001C14 880D[156B0100]      <1> 	mov	[p_crt_mode], cl ; reset ('case 3' end condition)
  1378                              <1> 
  1379                              <1> 	; restore cursor positions
  1380 00001C1A BE[1A6B0100]        <1> 	mov	esi, cursor_pposn
  1381 00001C1F BF[9E5E0100]        <1> 	mov	edi, CURSOR_POSN
  1382                              <1> 	;mov	ecx, 4	; restore all cursor positions (16 bytes)
  1383 00001C24 B104                <1> 	mov	cl, 4
  1384 00001C26 F3A5                <1> 	rep 	movsd
  1385                              <1> 	
  1386                              <1> 	;jmp	short _sm_23 ; do not clear current video pages
  1387                              <1> 
  1388                              <1> 	; 19/11/2020
  1389 00001C28 E956010000          <1> 	jmp	_set_active_page
  1390                              <1> 
  1391                              <1> _sm_21:
  1392                              <1> 	; 19/11/2020
  1393                              <1> 	; case 2 
  1394                              <1> 	;
  1395                              <1> 	; ([p_crt_mode] = 80h)
  1396                              <1> 	;
  1397                              <1> 	; User has requested to set video mode 3 again while
  1398                              <1> 	; current video mode is 3.. that means, set mode 03h
  1399                              <1> 	; parameters again and clear video page.
  1400                              <1> 	; ('noclearmem' option effects the result) 
  1401                              <1> 	
  1402                              <1> 	; 19/11/2020
  1403 00001C2D F605[176B0100]80    <1> 	test	byte [noclearmem], 80h
  1404 00001C34 7529                <1> 	jnz	short _sm_22	; 'do not clear video memory'
  1405                              <1> 				; continue with current text
  1406                              <1> 				; (user's option/choice) 
  1407                              <1> 	; clear video page
  1408                              <1> 	;mov	cx, [CRT_LEN] ; 4096
  1409                              <1> 	;shr	cx, 1 ; 2048 ; 16/11/2020
  1410 00001C36 66B82007            <1> 	mov	ax, 0720h
  1411                              <1> 	; 26/11/2020
  1412 00001C3A B900080000          <1> 	mov	ecx, 2048 ; 4096/2
  1413 00001C3F BF00800B00          <1> 	mov	edi, 0B8000h ; [crt_base]
  1414 00001C44 66033D[9C5E0100]    <1> 	add	di, [CRT_START]
  1415 00001C4B F366AB              <1> 	rep	stosw	; FILL THE REGEN BUFFER WITH BLANKS
  1416                              <1> 	;
  1417                              <1> 	; 19/11/2020
  1418 00001C4E A0[AE5E0100]        <1> 	mov	al, [ACTIVE_PAGE] ; 0 to 7 (for video mode 3)
  1419 00001C53 0FB6D8              <1> 	movzx	ebx, al
  1420 00001C56 D0E3                <1> 	shl	bl, 1
  1421 00001C58 66898B[9E5E0100]    <1> 	mov	[ebx+CURSOR_POSN], cx ; reset cursor position
  1422                              <1> _sm_22:
  1423                              <1> 	;mov	[p_crt_mode], al ; 0 ; reset
  1424                              <1> 	; 19/11/2020
  1425                              <1> 	;and	byte [p_crt_mode], 3 ; 83h -> 3, 80h -> 0  
  1426 00001C5F 8025[156B0100]7F    <1> 	and	byte [p_crt_mode], 7Fh ; 83h -> 3, 80h -> 0  
  1427                              <1> _sm_23:
  1428                              <1> 	; al = video page number
  1429                              <1> 	; [CRT_LEN] = length of regen buffer in bytes
  1430                              <1> 	;call	_set_active_page
  1431                              <1> 	; 16/11/2020
  1432 00001C66 E918010000          <1> 	jmp	_set_active_page
  1433                              <1> 
  1434                              <1> ;-----	NORMAL RETURN FROM ALL VIDEO RETURNS
  1435                              <1> 	;retn
  1436                              <1> 
  1437                              <1> cursor_shape_fix:
  1438                              <1> 	; 07/07/2016
  1439                              <1> 	; (Cursor start and cursor end line values -6,7-
  1440                              <1> 	; will be fixed depending on character height)
  1441                              <1> 	;
  1442                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  1443                              <1> 	; vgabios-0.7a (2011)
  1444                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  1445                              <1> 	; 'vgabios.c', ' biosfn_set_cursor_shape (CH,CL)'
  1446                              <1> 	;
  1447                              <1> 	; INPUT ->
  1448                              <1> 	;	AL = cursor start line (=6)
  1449                              <1> 	;	AH = cursor end line (=7)
  1450                              <1> 	; OUTPUT ->
  1451                              <1> 	;	AL = cursor start line (=14)
  1452                              <1> 	;	AH = cursor end line (=15)
  1453                              <1> 	;
  1454                              <1> 	;; if((modeset_ctl&0x01)&&(cheight>8)&&(CL<8)&&(CH<0x20))
  1455                              <1> 
  1456                              <1> 	;test	byte [VGA_MODESET_CTL], 1 ; VGA active
  1457                              <1> 	;jz	short csf_3
  1458 00001C6B 803D[7E660000]08    <1> 	cmp	byte [CHAR_HEIGHT], 8
  1459 00001C72 7649                <1> 	jna	short csf_3
  1460 00001C74 80FC08              <1> 	cmp	ah, 8
  1461 00001C77 7344                <1> 	jnb	short csf_3
  1462 00001C79 3C20                <1> 	cmp	al, 20h
  1463 00001C7B 7340                <1> 	jnb	short csf_3
  1464                              <1> 	;
  1465 00001C7D 6650                <1> 	push	ax
  1466                              <1> 	; {
  1467                              <1>    	; if(CL!=(CH+1))	
  1468 00001C7F FEC0                <1> 	inc	al
  1469 00001C81 38C4                <1> 	cmp	ah, al   ; ah != al + 1
  1470 00001C83 740F                <1>         je      short csf_1
  1471                              <1> 	; CH = ((CH+1) * cheight / 8) -1;
  1472 00001C85 8A25[7E660000]      <1> 	mov	ah, [CHAR_HEIGHT]
  1473 00001C8B F6E4                <1> 	mul	ah
  1474 00001C8D C0E803              <1> 	shr	al, 3 ; / 8
  1475 00001C90 FEC8                <1> 	dec	al ; - 1
  1476 00001C92 EB0E                <1> 	jmp	short csf_2 
  1477                              <1> csf_1: 	
  1478                              <1>  	; }
  1479                              <1>    	; else		; ah = al + 1
  1480                              <1>     	; {
  1481 00001C94 FEC4                <1> 	inc	ah	; ah = ah + 1   
  1482                              <1> 	; CH = ((CL+1) * cheight / 8) - 2;
  1483 00001C96 A0[7E660000]        <1> 	mov	al, [CHAR_HEIGHT]
  1484 00001C9B F6E4                <1> 	mul	ah
  1485 00001C9D C0E803              <1> 	shr	al, 3 ; / 8
  1486 00001CA0 2C02                <1> 	sub	al, 2 ; - 2
  1487                              <1> 	; al = 14 (if [CHAR_HEIGHT] = 16)
  1488                              <1> csf_2:
  1489 00001CA2 880424              <1> 	mov	[esp], al
  1490 00001CA5 8A642401            <1> 	mov	ah, [esp+1]
  1491                              <1> 	; CL = ((CL+1) * cheight / 8) - 1;
  1492 00001CA9 FEC4                <1> 	inc	ah 
  1493 00001CAB A0[7E660000]        <1> 	mov	al, [CHAR_HEIGHT]
  1494 00001CB0 F6E4                <1> 	mul	ah
  1495 00001CB2 C0E803              <1> 	shr	al, 3 ; / 8
  1496 00001CB5 FEC8                <1> 	dec	al ; - 1
  1497 00001CB7 88442401            <1> 	mov	[esp+1], al
  1498                              <1> 	; ah = 15 (if [CHAR_HEIGHT] = 16)
  1499                              <1> 	;
  1500 00001CBB 6658                <1> 	pop	ax
  1501                              <1> csf_3:
  1502 00001CBD C3                  <1> 	retn
  1503                              <1> 
  1504                              <1> SET_CTYPE:
  1505                              <1> 	; 12/09/2016
  1506                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1507 00001CBE 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7
  1508 00001CC5 0F878BFCFFFF        <1> 	ja	VIDEO_RETURN ; 12/09/2016
  1509 00001CCB E805000000          <1> 	call	_set_ctype
  1510 00001CD0 E981FCFFFF          <1>         jmp     VIDEO_RETURN
  1511                              <1> 
  1512                              <1> _set_ctype:
  1513                              <1> 	; 02/09/2014 (Retro UNIX 386 v1)
  1514                              <1> 	;
  1515                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1516                              <1> 
  1517                              <1> 	; (CH) = BITS 4-0 = START LINE FOR CURSOR
  1518                              <1> 	;  ** HARDWARE WILL ALWAYS CAUSE BLINK
  1519                              <1> 	;  ** SETTING BIT 5 OR 6 WILL CAUSE ERRATIC BLINKING
  1520                              <1> 	;     OR NO CURSOR AT ALL
  1521                              <1> 	; (CL) = BITS 4-0 = END LINE FOR CURSOR
  1522                              <1> 
  1523                              <1> ;------------------------------------------------
  1524                              <1> ; SET_CTYPE
  1525                              <1> ;	THIS ROUTINE SETS THE CURSOR VALUE
  1526                              <1> ; INPUT
  1527                              <1> ;	(CX) HAS CURSOR VALUE CH-START LINE, CL-STOP LINE
  1528                              <1> ; OUTPUT	
  1529                              <1> ;	NONE
  1530                              <1> ;------------------------------------------------
  1531                              <1> 
  1532                              <1> 	; 07/07/2016
  1533                              <1> 	; Fixing cursor start and stop line depending on
  1534                              <1> 	; current character height (=16)
  1535                              <1> 	; (Note: Default/initial values are 6 and 7.
  1536                              <1> 	; If set values are 6 (start) & 7 (stop) and 
  1537                              <1> 	; [CHAR_HEIGHT] = 16 :
  1538                              <1> 	; After fixing, start line will be 14, stop line
  1539                              <1> 	; will be 15.)
  1540 00001CD5 6689C8              <1> 	mov	ax, cx
  1541 00001CD8 86C4                <1> 	xchg	al, ah
  1542                              <1> 	; AL = start line, AH = stop line
  1543 00001CDA E88CFFFFFF          <1> 	call	cursor_shape_fix
  1544                              <1> 	; AL = start line (fixed), AH = stop line (fixed)
  1545 00001CDF 6689C1              <1> 	mov	cx, ax
  1546 00001CE2 86E9                <1> 	xchg	ch, cl
  1547                              <1> 	; CH = start line (fixed), CL = stop line (fixed)
  1548                              <1> 	;
  1549 00001CE4 B40A                <1> 	mov	ah, 10	; 6845 register for cursor set
  1550 00001CE6 66890D[93660000]    <1> 	mov	[CURSOR_MODE], cx ; save in data area
  1551                              <1> 	;call	m16	; output cx register
  1552                              <1> 	;retn
  1553 00001CED E9AC040000          <1>         jmp     m16
  1554                              <1> 
  1555                              <1> SET_CPOS:
  1556                              <1> 	; 12/09/2016
  1557                              <1> 	; 07/07/2016
  1558                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1559 00001CF2 80FF07              <1> 	cmp	bh, 7 ; video page > 7 ; 07/07/2016
  1560 00001CF5 0F875BFCFFFF        <1> 	ja	VIDEO_RETURN
  1561                              <1> 	;
  1562 00001CFB 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7
  1563 00001D02 770A                <1> 	ja	short vga_set_cpos ; 12/09/2016	
  1564 00001D04 E86A040000          <1> 	call	_set_cpos
  1565 00001D09 E948FCFFFF          <1>         jmp     VIDEO_RETURN
  1566                              <1> 
  1567                              <1> vga_set_cpos:
  1568                              <1> 	; 12/09/2016
  1569                              <1> 	; 09/07/2016
  1570                              <1> 	; set cursor position
  1571                              <1> 	; NOTE: Hardware cursor position will not be set
  1572                              <1> 	;   in any VGA modes (>7)
  1573                              <1> 	;   But, cursor position will be saved into
  1574                              <1> 	;   [CURSOR_POSN].
  1575                              <1> 	;   TRDOS 386 (TRDOS v2.0) uses only one page
  1576                              <1> 	;   (page 0) for all graphics modes.
  1577                              <1> 
  1578 00001D0E 668915[9E5E0100]    <1> 	mov	[CURSOR_POSN], dx ; save cursor pos for pg 0
  1579                              <1> 	; 04/08/2016
  1580                              <1> 	;mov	bh, [ACTIVE_PAGE] ; = 0
  1581                              <1> 	;call	_set_cpos
  1582 00001D15 E93CFCFFFF          <1> 	jmp     VIDEO_RETURN
  1583                              <1> 
  1584                              <1> READ_CURSOR:
  1585                              <1> 	; 12/09/2016
  1586                              <1> 	; 07/07/2016
  1587                              <1> 	; 12/05/2016
  1588                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1589                              <1> 	;
  1590                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1591                              <1> 
  1592                              <1> ;------------------------------------------------------
  1593                              <1> ; READ_CURSOR
  1594                              <1> ;	THIS ROUTINE READS THE CURRENT CURSOR VALUE FROM THE
  1595                              <1> ;	845, FORMATS IT, AND SENDS IT BACK TO THE CALLER
  1596                              <1> ; INPUT
  1597                              <1> ;	BH - PAGE OF CURSOR
  1598                              <1> ; OUTPUT
  1599                              <1> ;	DX - ROW, COLUMN OF THE CURRENT CURSOR POSITION
  1600                              <1> ;	CX - CURRENT CURSOR MODE
  1601                              <1> ;------------------------------------------------------
  1602                              <1> 
  1603                              <1> 	; BH = Video page number (0 to 7)
  1604                              <1> 
  1605                              <1> 	; 07/07/2016
  1606 00001D1A 80FF07              <1> 	cmp	bh, 7 ; video page > 7 (invalid)
  1607 00001D1D 7606                <1> 	jna	short read_cursor_1
  1608                              <1> 	; invalid video page (input) 
  1609 00001D1F 31C9                <1> 	xor	ecx, ecx ; 0
  1610 00001D21 31D2                <1> 	xor	edx, edx ; 0
  1611 00001D23 EB15                <1> 	jmp	short read_cursor_2
  1612                              <1> read_cursor_1:
  1613                              <1> 	; 12/09/2016
  1614 00001D25 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7 ; vga mode
  1615 00001D2C 7727                <1> 	ja	short vga_get_cpos
  1616                              <1> 	;
  1617 00001D2E E815000000          <1> 	call	get_cpos
  1618 00001D33 0FB70D[93660000]    <1> 	movzx	ecx, word [CURSOR_MODE]
  1619                              <1> read_cursor_2:
  1620 00001D3A 5D                  <1> 	pop	ebp
  1621 00001D3B 5F                  <1> 	pop	edi
  1622 00001D3C 5E                  <1> 	pop	esi
  1623 00001D3D 5B                  <1> 	pop	ebx
  1624 00001D3E 58                  <1> 	pop	eax  ; DISCARD SAVED CX AND DX
  1625 00001D3F 58                  <1> 	pop	eax
  1626 00001D40 A1[086B0100]        <1> 	mov	eax, [video_eax] ; 12/05/2016
  1627                              <1> 	;;15/01/2017
  1628                              <1> 	;;mov	byte [intflg], 0 ; 07/01/2017
  1629 00001D45 1F                  <1> 	pop	ds
  1630 00001D46 07                  <1> 	pop	es
  1631 00001D47 CF                  <1> 	iretd
  1632                              <1> 
  1633                              <1> get_cpos:
  1634                              <1> 	; 12/05/2016
  1635                              <1> 	; 16/01/2016
  1636                              <1> 	; BH = Video page number (0 to 7)
  1637                              <1> 	;
  1638 00001D48 D0E7                <1> 	shl	bh, 1 ; WORD OFFSET
  1639 00001D4A 0FB6F7              <1> 	movzx	esi, bh 
  1640 00001D4D 0FB796[9E5E0100]    <1> 	movzx	edx, word [esi+CURSOR_POSN]
  1641 00001D54 C3                  <1> 	retn
  1642                              <1> 
  1643                              <1> vga_get_cpos:
  1644                              <1> 	; 12/09/2016
  1645                              <1> 	; get cursor position (vga)
  1646 00001D55 0FB715[9E5E0100]    <1> 	movzx	edx, word [CURSOR_POSN] ; cursor pos for pg 0
  1647 00001D5C 31C9                <1> 	xor	ecx, ecx ; Cursor Mode = 0 (invalid)
  1648 00001D5E EBDA                <1> 	jmp     short read_cursor_2
  1649                              <1> 
  1650                              <1> ACT_DISP_PAGE:
  1651                              <1> 	; 07/07/2016
  1652                              <1> 	; 26/06/2016
  1653                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1654                              <1> 	;
  1655                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1656                              <1> 	;
  1657                              <1> ;-----------------------------------------------------
  1658                              <1> ; ACT_DISP_PAGE
  1659                              <1> ;	THIS ROUTINE SETS THE ACTIVE DISPLAY PAGE, ALLOWING
  1660                              <1> ;	THE FULL USE OF THE MEMORY SET ASIDE FOR THE VIDEO ATTACHMENT
  1661                              <1> ; INPUT
  1662                              <1> ;	AL HAS THE NEW ACTIVE DISPLAY PAGE
  1663                              <1> ; OUTPUT
  1664                              <1> ;	THE 6845 IS RESET TO DISPLAY THAT PAGE
  1665                              <1> ;-----------------------------------------------------
  1666                              <1> 	; 07/07/2016
  1667 00001D60 3C07                <1> 	cmp	al, 7	; > 7 = invalid video page number
  1668                              <1> 	;ja	VIDEO_RETURN
  1669 00001D62 7715                <1>         ja	short adp_2 ; 18/11/2020
  1670                              <1> 	;cmp	byte [CRT_MODE], 3
  1671                              <1> 	;je	short adp_1
  1672                              <1> 	; 18/11/2020
  1673 00001D64 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE]
  1674 00001D6A 80FC03              <1> 	cmp	ah, 3
  1675 00001D6D 7605                <1> 	jna	short adp_1 ; mode 01h, 00h (01h), 02h (03h), 03h
  1676 00001D6F 80FC07              <1> 	cmp	ah, 7	    ; mode 07h (03h)	
  1677 00001D72 7505                <1> 	jne	short adp_2
  1678                              <1> 	;and 	al, al
  1679                              <1>         ;jnz	VIDEO_RETURN
  1680                              <1> 	;;sub	al, al ; 0 ; force to page 0
  1681                              <1> adp_1:	
  1682 00001D74 E805000000          <1> 	call	set_active_page
  1683                              <1> adp_2:
  1684 00001D79 E9D8FBFFFF          <1>         jmp     VIDEO_RETURN
  1685                              <1> 
  1686                              <1> set_active_page:   ; tty_sw
  1687                              <1> 	; 09/12/2017
  1688                              <1> 	; 26/07/2016
  1689                              <1> 	; 26/06/2016
  1690                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1691                              <1> 	; 30/06/2015
  1692                              <1> 	; 04/03/2014  (act_disp_page --> tty_sw)
  1693                              <1> 	; 10/12/2013
  1694                              <1> 	; 04/12/2013
  1695                              <1> 	;
  1696 00001D7E A2[AE5E0100]        <1> 	mov	[ACTIVE_PAGE], al ; save active page value ; [ptty]
  1697                              <1> _set_active_page:
  1698                              <1> 	; 27/06/2015
  1699 00001D83 0FB6D8              <1> 	movzx	ebx, al
  1700                              <1> 	;
  1701                              <1> 	;cbw	; 07/09/2014 (ah=0)
  1702 00001D86 28E4                <1> 	sub	ah, ah ; 09/12/2017
  1703 00001D88 66F725[186B0100]    <1> 	mul	word [CRT_LEN]  ; get saved length of regen buffer
  1704                              <1> 				; display page times regen length
  1705                              <1> 	; 10/12/2013
  1706 00001D8F 66A3[9C5E0100]      <1> 	mov	[CRT_START], ax ; save start address for later
  1707 00001D95 6689C1              <1> 	mov	cx, ax ; start address to cx
  1708                              <1> _M16:
  1709                              <1> 	;sar	cx, 1
  1710 00001D98 66D1E9              <1> 	shr	cx, 1	; divide by 2 for 6845 handling
  1711 00001D9B B40C                <1> 	mov	ah, 12	; 6845 register for start address
  1712 00001D9D E8FC030000          <1> 	call	m16
  1713                              <1> 	;sal	bx, 1
  1714                              <1> 	; 01/09/2014
  1715 00001DA2 D0E3                <1> 	shl	bl, 1	; *2 for word offset
  1716 00001DA4 81C3[9E5E0100]      <1> 	add	ebx, CURSOR_POSN
  1717 00001DAA 668B13              <1> 	mov	dx, [ebx] ; get cursor for this page
  1718                              <1> 	; 16/01/2016
  1719                              <1> 	;call	m18
  1720                              <1> 	;retn
  1721 00001DAD E9D8030000          <1> 	jmp	m18
  1722                              <1> 
  1723                              <1> position:
  1724                              <1> 	; 24/06/2016
  1725                              <1> 	; 12/05/2016 - TRDOS 386 (TRDOS v2.0)
  1726                              <1> 	; 27/06/2015
  1727                              <1> 	; 02/09/2014
  1728                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  1729                              <1> 	; 04/12/2013 (Retro UNIX 8086 v1)
  1730                              <1> 	;
  1731                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1732                              <1> 	;
  1733                              <1> ;-----------------------------------------
  1734                              <1> ; POSITION
  1735                              <1> ;	THIS SERVICE ROUTINE CALCULATES THE REGEN BUFFER ADDRESS
  1736                              <1> ;	OF A CHARACTER IN THE ALPHA MODE
  1737                              <1> ; INPUT
  1738                              <1> ;	AX = ROW, COLUMN POSITION
  1739                              <1> ; OUTPUT
  1740                              <1> ;	AX = OFFSET OF CHAR POSITION IN REGEN BUFFER
  1741                              <1> ;-----------------------------------------
  1742                              <1> 
  1743                              <1> 	; DX = ROW, COLUMN POSITION
  1744 00001DB2 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS] ; 24/06/2016
  1745 00001DB9 F6E6                <1> 	mul	dh	 ; row value
  1746 00001DBB 30F6                <1> 	xor	dh, dh   ; 0	
  1747 00001DBD 6601D0              <1> 	add	ax, dx	 ; add column value to the result
  1748 00001DC0 66D1E0              <1> 	shl	ax, 1	; * 2 for attribute bytes
  1749                              <1> 		; EAX = AX = OFFSET OF CHAR POSITION IN REGEN BUFFER 
  1750 00001DC3 C3                  <1> 	retn
  1751                              <1> 
  1752                              <1> find_position:
  1753                              <1> 	; 24/06/2016
  1754                              <1> 	; 12/05/2016 - TRDOS 386 (TRDOS v2.0)
  1755                              <1> 	; 27/06/2015
  1756                              <1> 	; 07/09/2014
  1757                              <1> 	; 02/09/2014
  1758                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  1759                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1760                              <1> 
  1761 00001DC4 0FB6CF              <1> 	movzx	ecx, bh ; video page number
  1762 00001DC7 89CE                <1> 	mov	esi, ecx
  1763 00001DC9 66D1E6              <1> 	shl	si, 1
  1764 00001DCC 668B96[9E5E0100]    <1> 	mov	dx, [esi+CURSOR_POSN]
  1765 00001DD3 740C                <1> 	jz	short p21
  1766 00001DD5 6631F6              <1> 	xor	si, si
  1767                              <1> p20:
  1768 00001DD8 660335[186B0100]    <1> 	add	si, [CRT_LEN] ; 24/06/2016
  1769                              <1> 	;add	si, 80*25*2 ; add length of buffer for one page		
  1770 00001DDF E2F7                <1> 	loop	p20
  1771                              <1> p21:
  1772 00001DE1 6621D2              <1> 	and	dx, dx
  1773 00001DE4 7407                <1> 	jz	short p22
  1774 00001DE6 E8C7FFFFFF          <1> 	call 	position ; determine location in regen in page
  1775 00001DEB 01C6                <1> 	add	esi, eax ; add location to start of regen page
  1776                              <1> p22:	
  1777                              <1> 	;mov	dx, [addr_6845] ; get base address of active display			
  1778                              <1> 	;mov	dx, 03D4h ; I/O address of color card
  1779                              <1> 	;add	dx, 6	; point at status port
  1780 00001DED 66BADA03            <1> 	mov	dx, 03DAh ; status port
  1781                              <1> 	; cx = 0
  1782 00001DF1 C3                  <1> 	retn
  1783                              <1> 
  1784                              <1> SCROLL_UP:
  1785                              <1> 	; 07/07/2016
  1786                              <1> 	; 26/06/2016
  1787                              <1> 	; 12/05/2016
  1788                              <1> 	; 30/01/2016
  1789                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1790                              <1> 	; 07/09/2014
  1791                              <1> 	; 02/09/2014
  1792                              <1> 	; 01/09/2014 (Retro UNIX 386 v1 - beginning)
  1793                              <1> 	; 04/04/2014
  1794                              <1> 	; 04/12/2013
  1795                              <1> 	;
  1796                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  1797                              <1> 	;
  1798                              <1> ;----------------------------------------------
  1799                              <1> ; SCROLL UP
  1800                              <1> ;	THIS ROUTINE MOVES A BLOCK OF CHARACTERS UP
  1801                              <1> ;	ON THE SCREEN
  1802                              <1> ; INPUT
  1803                              <1> ;	(AH) = CURRENT CRT MODE
  1804                              <1> ;	(AL) = NUMBER OF ROWS TO SCROLL
  1805                              <1> ;	(CX) = ROW/COLUMN OF UPPER LEFT CORNER
  1806                              <1> ;	(DX) = ROW/COLUMN OF LOWER RIGHT CORNER
  1807                              <1> ;	(BH) = ATTRIBUTE TO BE USED ON BLANKED LINE
  1808                              <1> ;	(DS) = DATA SEGMENT
  1809                              <1> ;	(ES) = REGEN BUFFER SEGMENT
  1810                              <1> ; OUTPUT
  1811                              <1> ;	NONE -- THE REGEN BUFFER IS MODIFIED
  1812                              <1> ;--------------------------------------------
  1813                              <1> 
  1814                              <1> 	; 07/07/2016
  1815 00001DF2 38F5                <1> 	cmp	ch, dh
  1816 00001DF4 0F875CFBFFFF        <1> 	ja	VIDEO_RETURN
  1817 00001DFA 38D1                <1> 	cmp	cl, dl
  1818 00001DFC 0F8754FBFFFF        <1> 	ja	VIDEO_RETURN
  1819                              <1> 	;
  1820 00001E02 E805000000          <1> 	call	_scroll_up
  1821 00001E07 E94AFBFFFF          <1>         jmp     VIDEO_RETURN
  1822                              <1> 
  1823                              <1> _scroll_up:  ; from 'write_tty'
  1824                              <1> 	;
  1825                              <1> 	; cl = left upper column
  1826                              <1> 	; ch = left upper row
  1827                              <1> 	; dl = right lower column
  1828                              <1> 	; dh = right lower row
  1829                              <1> 	;
  1830                              <1> 	; al = line count 
  1831                              <1> 	; bl = attribute to be used on blanked line	
  1832                              <1> 	; bh = video page number (0 to 7)
  1833                              <1> 
  1834 00001E0C E89C000000          <1> 	call	test_line_count ; 16/01/2016
  1835                              <1> 
  1836 00001E11 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE] ; current video mode	
  1837                              <1> 	;;cmp	byte [CRT_MODE], 4
  1838                              <1> 	;cmp	ah, 4 ; 07/07/2016
  1839                              <1> 	;jnb	GRAPHICS_UP ; 26/06/2016
  1840                              <1> 	; 18/11/2020
  1841 00001E17 80FC04              <1> 	cmp	ah, 4
  1842 00001E1A 720A                <1>  	jb	short n0	
  1843 00001E1C 80FC07              <1> 	cmp	ah, 7 ; TEST FOR BW CARD 
  1844                              <1> 		      ;	(80x25 text, mono)
  1845 00001E1F 7405                <1> 	je	short n0 ; same with mode 3 for TRDOS 386
  1846 00001E21 E949050000          <1> 	jmp	GRAPHICS_UP
  1847                              <1> n0:
  1848                              <1> 	; 07/07/2016
  1849 00001E26 80FF07              <1> 	cmp	bh, 7 ; video page number
  1850 00001E29 7606                <1> 	jna	short n1
  1851 00001E2B 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE]
  1852                              <1> n1:
  1853 00001E31 88DC                <1> 	mov	ah, bl ; attribute
  1854 00001E33 6650                <1> 	push	ax ; *
  1855                              <1> 	;mov 	esi, [CRT_BASE]
  1856 00001E35 BE00800B00          <1>         mov     esi, 0B8000h  
  1857 00001E3A 3A3D[AE5E0100]      <1>         cmp     bh, [ACTIVE_PAGE]
  1858 00001E40 750B                <1> 	jne	short n2
  1859                              <1> 	;
  1860 00001E42 66A1[9C5E0100]      <1>         mov     ax, [CRT_START]
  1861 00001E48 6601C6              <1>         add     si, ax
  1862 00001E4B EB11                <1>         jmp     short n4
  1863                              <1> n2:
  1864 00001E4D 20FF                <1>         and     bh, bh
  1865 00001E4F 740D                <1> 	jz	short n4
  1866 00001E51 88F8                <1> 	mov	al, bh
  1867                              <1> n3:
  1868 00001E53 660335[186B0100]    <1>         add	si, [CRT_LEN]
  1869 00001E5A FEC8                <1>         dec	al
  1870 00001E5C 75F5                <1> 	jnz	short n3
  1871                              <1> n4:	
  1872 00001E5E E85D000000          <1> 	call	scroll_position ; 16/01/2016
  1873 00001E63 7420                <1>         jz      short n6 
  1874                              <1> 
  1875 00001E65 01CE                <1>         add     esi, ecx ; from address for scroll
  1876 00001E67 88F5                <1> 	mov	ch, dh  ; #rows in block
  1877 00001E69 28C5                <1> 	sub	ch, al	; #rows to be moved
  1878                              <1> n5:
  1879 00001E6B E894000000          <1> 	call	n10 ; 16/01/2016
  1880                              <1> 	
  1881 00001E70 51                  <1>         push	ecx
  1882 00001E71 0FB60D[7C660000]    <1> 	movzx	ecx, byte [CRT_COLS] 
  1883 00001E78 00C9                <1> 	add	cl, cl
  1884 00001E7A 01CE                <1>         add	esi, ecx  ; next line
  1885 00001E7C 01CF                <1>         add	edi, ecx
  1886 00001E7E 59                  <1> 	pop	ecx
  1887                              <1> 
  1888 00001E7F FECD                <1> 	dec	ch	 ; count of lines to move
  1889 00001E81 75E8                <1> 	jnz	short n5 ; row loop
  1890                              <1> 	; ch = 0
  1891 00001E83 88C6                <1> 	mov	dh, al	 ; #rows	
  1892                              <1> n6:
  1893                              <1> 	; attribute in ah
  1894 00001E85 B020                <1> 	mov	al, ' '	 ; fill with blanks
  1895                              <1> n7:
  1896 00001E87 E885000000          <1> 	call	n11 ; 16/01/2016
  1897                              <1> 
  1898 00001E8C 8A0D[7C660000]      <1> 	mov	cl, [CRT_COLS]
  1899 00001E92 00C9                <1> 	add	cl, cl
  1900 00001E94 01CF                <1>         add	edi, ecx
  1901                              <1> 
  1902 00001E96 FECE                <1> 	dec	dh
  1903 00001E98 75ED                <1> 	jnz	short n7
  1904                              <1> n16:
  1905 00001E9A 3A3D[AE5E0100]      <1> 	cmp	bh, [ACTIVE_PAGE]
  1906 00001EA0 750A                <1> 	jne	short n8
  1907                              <1> 	
  1908                              <1> 	;cmp	byte [CRT_MODE], 7 ; is this the black and white card
  1909                              <1> 	;je	short n8	   ; if so, skip the mode reset
  1910                              <1> 
  1911 00001EA2 A0[7B660000]        <1> 	mov	al, [CRT_MODE_SET] ; get the value of mode set
  1912 00001EA7 66BAD803            <1> 	mov	dx, 03D8h ; always set color card port
  1913 00001EAB EE                  <1> 	out	dx, al
  1914                              <1> n8:
  1915 00001EAC C3                  <1> 	retn
  1916                              <1> 
  1917                              <1> test_line_count:
  1918                              <1> 	; 12/05/2016
  1919                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1920                              <1> 	; 07/09/2014 (scroll_up)
  1921 00001EAD 08C0                <1> 	or	al, al
  1922 00001EAF 740E                <1> 	jz	short al_set2
  1923 00001EB1 6652                <1> 	push	dx
  1924 00001EB3 28EE                <1> 	sub	dh, ch  ; subtract upper row from lower row number
  1925 00001EB5 FEC6                <1> 	inc	dh	; adjust difference by 1
  1926 00001EB7 38C6                <1> 	cmp	dh, al 	; line count = amount of rows in window?
  1927 00001EB9 7502                <1> 	jne	short al_set1 ; if not the we're all set
  1928 00001EBB 30C0                <1> 	xor	al, al	; otherwise set al to zero
  1929                              <1> al_set1:
  1930 00001EBD 665A                <1> 	pop	dx
  1931                              <1> al_set2:
  1932 00001EBF C3                  <1> 	retn
  1933                              <1> 
  1934                              <1> scroll_position:
  1935                              <1> 	; 26/06/2016
  1936                              <1> 	; 30/01/2016
  1937                              <1>         ; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  1938                              <1> 	; 07/09/2014 (scroll_up)
  1939                              <1> 
  1940 00001EC0 6652                <1> 	push	dx
  1941 00001EC2 6689CA              <1> 	mov	dx, cx	; now, upper left position in DX
  1942 00001EC5 E8E8FEFFFF          <1> 	call	position
  1943 00001ECA 01C6                <1> 	add	esi, eax
  1944 00001ECC 89F7                <1> 	mov	edi, esi
  1945 00001ECE 665A                <1> 	pop	dx	; lower right position in DX
  1946 00001ED0 6629CA              <1> 	sub	dx, cx
  1947 00001ED3 FEC6                <1> 	inc	dh	; dh = #rows 
  1948 00001ED5 FEC2                <1> 	inc	dl	; dl = #cols in block
  1949 00001ED7 59                  <1> 	pop	ecx 	; return address
  1950 00001ED8 6658                <1> 	pop	ax	; * ; al = line count, ah = attribute
  1951 00001EDA 51                  <1> 	push	ecx	; return address
  1952 00001EDB 0FB7C8              <1> 	movzx	ecx, ax
  1953 00001EDE 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS]
  1954 00001EE4 F6E4                <1> 	mul	ah	; determine offset to from address
  1955 00001EE6 6601C0              <1> 	add	ax, ax  ; *2 for attribute byte
  1956                              <1> 	;
  1957 00001EE9 6650                <1> 	push	ax	; offset 
  1958 00001EEB 6652                <1> 	push	dx
  1959                              <1> 	;
  1960                              <1> 	; 04/04/2014
  1961 00001EED 66BADA03            <1> 	mov	dx, 3DAh ; guaranteed to be color card here	
  1962                              <1> n9:                      ; wait_display_enable
  1963 00001EF1 EC                  <1>         in      al, dx   ; get port
  1964 00001EF2 A808                <1> 	test	al, RVRT ; wait for vertical retrace	
  1965 00001EF4 74FB                <1> 	jz	short n9 ; wait_display_enable
  1966 00001EF6 B025                <1> 	mov	al, 25h
  1967 00001EF8 B2D8                <1> 	mov	dl, 0D8h ; address control port
  1968 00001EFA EE                  <1> 	out	dx, al	; turn off video during vertical retrace
  1969 00001EFB 665A                <1> 	pop	dx	; #rows, #cols
  1970 00001EFD 6658                <1>        	pop	ax	; offset
  1971 00001EFF 6691                <1> 	xchg	ax, cx	; 
  1972                              <1> 	; ecx = offset, al = line count, ah = attribute
  1973                              <1> 	;
  1974 00001F01 08C0                <1> 	or	al, al
  1975 00001F03 C3                  <1> 	retn
  1976                              <1> n10:
  1977                              <1> 	; Move rows
  1978 00001F04 88D1                <1> 	mov	cl, dl	; get # of cols to move
  1979 00001F06 56                  <1> 	push	esi
  1980 00001F07 57                  <1> 	push	edi	; save start address
  1981                              <1> n10r:
  1982 00001F08 66A5                <1> 	movsw		; move that line on screen
  1983 00001F0A FEC9                <1> 	dec	cl
  1984 00001F0C 75FA                <1>         jnz     short n10r
  1985 00001F0E 5F                  <1> 	pop	edi
  1986 00001F0F 5E                  <1> 	pop	esi	; recover addresses
  1987 00001F10 C3                  <1> 	retn
  1988                              <1> n11:
  1989                              <1> 	; Clear rows
  1990                              <1>                 	; dh =  #rows
  1991 00001F11 88D1                <1>         mov	cl, dl	; get # of cols to clear
  1992 00001F13 57                  <1>         push    edi     ; save address
  1993                              <1> n11r:
  1994 00001F14 66AB                <1>         stosw           ; store fill character
  1995 00001F16 FEC9                <1> 	dec	cl
  1996 00001F18 75FA                <1>         jnz     short n11r
  1997 00001F1A 5F                  <1>         pop     edi     ; recover address
  1998 00001F1B C3                  <1> 	retn
  1999                              <1> 
  2000                              <1> SCROLL_DOWN:
  2001                              <1> 	; 07/07/2016
  2002                              <1> 	; 27/06/2016
  2003                              <1> 	; 26/06/2016
  2004                              <1> 	; 12/05/2016
  2005                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2006                              <1> 	;
  2007                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  2008                              <1> 
  2009                              <1> ;------------------------------------------
  2010                              <1> ; SCROLL DOWN
  2011                              <1> ;	THIS ROUTINE MOVES THE CHARACTERS WITHIN A DEFINED
  2012                              <1> ;	BLOCK DOWN ON THE SCREEN, FILLING THE TOP LINES
  2013                              <1> ;	WITH A DEFINED CHARACTER
  2014                              <1> ; INPUT
  2015                              <1> ;	(AH) = CURRENT CRT MODE
  2016                              <1> ;	(AL) = NUMBER OF LINES TO SCROLL
  2017                              <1> ;	(CX) = UPPER LEFT CORNER OF RECION
  2018                              <1> ;	(DX) = LOWER RIGHT CORNER OF REGION
  2019                              <1> ;	(BH) = FILL CHARACTER
  2020                              <1> ;	(DS) = DATA SEGMENT
  2021                              <1> ;	(ES) = REGEN SEGMENT
  2022                              <1> ; OUTPUT
  2023                              <1> ;	NONE -- SCREEN IS SCROLLED
  2024                              <1> ;------------------------------------------
  2025                              <1> 
  2026                              <1> 	; 07/07/2016
  2027 00001F1C 38F5                <1> 	cmp	ch, dh
  2028                              <1> 	;ja	VIDEO_RETURN
  2029 00001F1E 7709                <1> 	ja	short _s_d_retn ; 18/11/2020
  2030 00001F20 38D1                <1> 	cmp	cl, dl
  2031                              <1> 	;ja	VIDEO_RETURN
  2032 00001F22 7705                <1> 	ja	short _s_d_retn ; 18/11/2020
  2033                              <1> 	;
  2034 00001F24 E805000000          <1> 	call	_scroll_down
  2035                              <1> _s_d_retn:
  2036 00001F29 E928FAFFFF          <1>         jmp     VIDEO_RETURN
  2037                              <1> 
  2038                              <1> _scroll_down: ; 27/06/2016
  2039                              <1> 
  2040                              <1> 	; cl = left upper column
  2041                              <1> 	; ch = left upper row
  2042                              <1> 	; dl = right lower column
  2043                              <1> 	; dh = right lower row
  2044                              <1> 	;
  2045                              <1> 	; al = line count 
  2046                              <1> 	; bl = attribute to be used on blanked line	
  2047                              <1> 	; bh = video page number (0 to 7)
  2048                              <1> 
  2049                              <1> 	; !!!!
  2050 00001F2E FD                  <1> 	std		; DIRECTION FOR SCROLL DOWN
  2051                              <1> 	; !!!!
  2052 00001F2F E879FFFFFF          <1> 	call	test_line_count ; 16/01/2016
  2053                              <1> 	
  2054 00001F34 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE] ; current video mode	
  2055                              <1> 	;;cmp	byte [CRT_MODE], 4
  2056                              <1> 	;cmp	ah, 4 ; 07/07/2016
  2057                              <1> 	;jnb	GRAPHICS_DOWN ; 26/06/2016
  2058                              <1> 	; 18/11/2020
  2059 00001F3A 80FC04              <1> 	cmp	ah, 4
  2060 00001F3D 720A                <1>  	jb	short _n0	
  2061 00001F3F 80FC07              <1> 	cmp	ah, 7 ; TEST FOR BW CARD 
  2062                              <1> 		      ;	(80x25 text, mono)
  2063 00001F42 7405                <1> 	je	short _n0 ; same with mode 3 for TRDOS 386
  2064 00001F44 E90A080000          <1> 	jmp	GRAPHICS_DOWN
  2065                              <1> _n0:
  2066                              <1> 	; 07/07/2016
  2067 00001F49 80FF07              <1> 	cmp	bh, 7 ; video page number
  2068 00001F4C 7606                <1> 	jna	short n12
  2069 00001F4E 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE]
  2070                              <1> 	;
  2071                              <1> n12:			; CONTINUE_DOWN
  2072 00001F54 88DC                <1> 	mov	ah, bl
  2073 00001F56 6650                <1> 	push	ax	; * ; save attribute in ah
  2074 00001F58 6689D0              <1> 	mov	ax, dx	; LOWER RIGHT CORNER
  2075 00001F5B E860FFFFFF          <1> 	call	scroll_position	; GET REGEN LOCATION
  2076 00001F60 741F                <1> 	jz	short n14
  2077 00001F62 29CE                <1> 	sub	esi, ecx  ; SI IS FROM ADDRESS
  2078 00001F64 88F5                <1> 	mov	ch, dh  ; #rows in block
  2079 00001F66 28C5                <1> 	sub	ch, al	; #rows to be moved
  2080                              <1> n13:
  2081 00001F68 E897FFFFFF          <1> 	call	n10	; MOVE ONE ROW
  2082                              <1> 
  2083 00001F6D 51                  <1> 	push	ecx
  2084 00001F6E 8A0D[7C660000]      <1> 	mov	cl, [CRT_COLS] 
  2085 00001F74 00C9                <1> 	add	cl, cl
  2086 00001F76 29CE                <1>         sub	esi, ecx  ; next line
  2087 00001F78 29CF                <1>         sub	edi, ecx
  2088 00001F7A 59                  <1>         pop	ecx
  2089                              <1> 	
  2090 00001F7B FECD                <1> 	dec	ch	 ; count of lines to move
  2091 00001F7D 75E9                <1> 	jnz	short n13 ; row loop
  2092                              <1> 	; ch = 0
  2093 00001F7F 88C6                <1> 	mov	dh, al	 ; #rows
  2094                              <1> n14:
  2095                              <1> 	; attribute in ah
  2096 00001F81 B020                <1> 	mov	al, ' '	 ; fill with blanks
  2097                              <1> n15:
  2098 00001F83 E889FFFFFF          <1> 	call	n11 ; 16/01/2016
  2099                              <1> 
  2100 00001F88 8A0D[7C660000]      <1> 	mov	cl, [CRT_COLS]
  2101 00001F8E 00C9                <1> 	add	cl, cl
  2102 00001F90 29CF                <1>         sub	edi, ecx
  2103                              <1>         
  2104 00001F92 FECE                <1> 	dec	dh
  2105 00001F94 75ED                <1> 	jnz	short n15
  2106                              <1> 	;
  2107                              <1> 	; 18/11/2020
  2108 00001F96 FC                  <1> 	cld	; clear direction flag	
  2109                              <1> 	;
  2110 00001F97 E9FEFEFFFF          <1> 	jmp	n16 ; 27/06/2016
  2111                              <1> 
  2112                              <1> ;	cmp	bh, [ACTIVE_PAGE]
  2113                              <1> ;	jne	short n16
  2114                              <1> ;
  2115                              <1> ;	;cmp	byte [CRT_MODE], 7	; is this the black and white card
  2116                              <1> ;	;je	short n16		; if so, skip the mode reset
  2117                              <1> ;
  2118                              <1> ;	mov	al, [CRT_MODE_SET] ; get the value of mode set
  2119                              <1> ;	mov	dx, 03D8h ; always set color card port
  2120                              <1> ;	out	dx, al
  2121                              <1> ;n16:
  2122                              <1> ;	; !!!!
  2123                              <1> ;	cld		; Clear direction flag !
  2124                              <1> ;	; !!!!
  2125                              <1> ;	retn
  2126                              <1> 
  2127                              <1> READ_AC_CURRENT:
  2128                              <1> 	; 08/07/2016
  2129                              <1> 	; 26/06/2016
  2130                              <1> 	; 12/05/2016
  2131                              <1> 	; 18/01/2016
  2132                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2133                              <1> 	;
  2134                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  2135                              <1> 	;
  2136                              <1> 	; 08/07/2016
  2137 00001F9C 803D[7A660000]07    <1>         cmp     byte [CRT_MODE], 7 ; 6!?
  2138 00001FA3 7607                <1> 	jna	short read_ac_c
  2139 00001FA5 31C0                <1> 	xor	eax, eax
  2140 00001FA7 E9AFF9FFFF          <1>         jmp     _video_return 
  2141                              <1> read_ac_c:
  2142 00001FAC E805000000          <1> 	call	_read_ac_current
  2143                              <1> 	; 12/05/2016
  2144                              <1>         ;jmp     VIDEO_RETURN
  2145 00001FB1 E9A5F9FFFF          <1> 	jmp	_video_return
  2146                              <1> 
  2147                              <1> ;------------------------------------------------------------------------
  2148                              <1> ; READ_AC_CURRENT							:
  2149                              <1> ;	THIS ROUTINE READS THE ATTRIBUTE AND CHARACTER AT THE CURRENT	:
  2150                              <1> ;	CURSOR POSITION AND RETURNS THEM TO THE CALLER			:
  2151                              <1> ; INPUT									:
  2152                              <1> ;	(AH) = CURRENT CRT MODE						:
  2153                              <1> ;	(BH) = DISPLAY PAGE ( ALPHA MODES ONLY )			:
  2154                              <1> ;	(DS) = DATA SEGMENT						:
  2155                              <1> ;	(ES) = REGEN SEGMENT						:
  2156                              <1> ; OUTPUT								:
  2157                              <1> ;	(AL) = CHARACTER READ						:
  2158                              <1> ;	(AH) = ATTRIBUTE READ						:
  2159                              <1> ;------------------------------------------------------------------------
  2160                              <1> 
  2161                              <1> _read_ac_current:
  2162                              <1> 	; 26/06/2016
  2163                              <1> 	; 12/05/2016 
  2164                              <1> 	; 18/01/2016
  2165                              <1> 
  2166 00001FB6 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE] ; current video mode	
  2167 00001FBC 80FC04              <1> 	cmp	ah, 4
  2168 00001FBF 720A                <1>  	jb	short p10
  2169                              <1> 	; 18/11/2020
  2170                              <1> 	;cmp	byte [CRT_MODE], 4
  2171                              <1> 	;jnb     GRAPHICS_READ ; 26/06/2016
  2172                              <1> 
  2173 00001FC1 80FC07              <1> 	cmp	ah, 7 ; TEST FOR BW CARD (80x25 monochrome text)
  2174 00001FC4 7405                <1> 	je	short p10	 ; same with mode 3 in TRDOS 386
  2175 00001FC6 E9DE080000          <1> 	jmp	GRAPHICS_READ
  2176                              <1> p10:
  2177 00001FCB E8F4FDFFFF          <1> 	call	find_position	; GET REGEN LOCATION AND PORT ADDRESS
  2178                              <1> 	;
  2179                              <1> 	; esi = regen location
  2180                              <1> 	; dx = status port
  2181                              <1> 	;
  2182                              <1> 
  2183                              <1> 	; 18/11/2020
  2184                              <1> 	; convert display mode to a zero value 
  2185                              <1> 	; for 80 column color mode
  2186                              <1> 	;mov	ah, [CRT_MODE]	
  2187                              <1> 	;sub	ah, 2
  2188                              <1> 	;shr	ah, 1
  2189                              <1> 	;jnz	short p13
  2190                              <1> 
  2191                              <1> 	; 18/11/2020 (TRDOS 386 v2.0.3)
  2192 00001FD0 30DB                <1> 	xor	bl, bl	; 0
  2193 00001FD2 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 03h ; 80x25 color text
  2194 00001FD9 7404                <1> 	je	short p11    ; Note: Only mode 03h and mode 01h are
  2195 00001FDB FEC3                <1> 	inc	bl	; 1  ;       in use by TRDOS 386 as text modes	
  2196 00001FDD EB18                <1> 	jmp	short p14    ;       (07h, 00h and 02h are redirected)		
  2197                              <1> 
  2198                              <1> 	; WAIT FOR HORIZONTAL RETRACE OR VERTICAL RETRACE IF COLOR 80
  2199                              <1> p11:
  2200 00001FDF FB                  <1> 	sti		; enable interrupts first
  2201                              <1> 	; 18/11/2020
  2202 00001FE0 08DB                <1> 	or	bl, bl
  2203 00001FE2 7514                <1> 	jnz	short p13 ; mode 01h (and mode 00h) - 40x25 color text
  2204                              <1> 	;
  2205 00001FE4 3A3D[AE5E0100]      <1> 	cmp     bh, [ACTIVE_PAGE]
  2206 00001FEA 750C                <1> 	jne	short p13 
  2207 00001FEC FA                  <1> 	cli 		; block interrupts for single loop
  2208 00001FED EC                  <1> 	in	al, dx	; get status from the adapter
  2209 00001FEE A801                <1> 	test	al, RHRZ ; is horizontal retrace low
  2210 00001FF0 75ED                <1> 	jnz	short p11 ; wait until it is
  2211                              <1> p12:			;  wait for either retrace high
  2212 00001FF2 EC                  <1> 	in	al, dx ; get status again
  2213 00001FF3 A809                <1> 	test	al, RVRT+RHRZ ; is horizontal or vertical retrace high
  2214 00001FF5 74FB                <1> 	jz	short p12 ; wait until either retrace active
  2215                              <1> p14:
  2216 00001FF7 FB                  <1> 	sti
  2217                              <1> p13:
  2218 00001FF8 81C600800B00        <1> 	add	esi, 0B8000h 
  2219 00001FFE 668B06              <1> 	mov	ax, [esi]
  2220                              <1> 
  2221 00002001 C3                  <1> 	retn	; 18/01/2016
  2222                              <1> 
  2223                              <1> WRITE_AC_CURRENT:
  2224                              <1> 	; 08/07/2016
  2225                              <1> 	; 26/06/2016
  2226                              <1> 	; 24/06/2016
  2227                              <1> 	; 12/05/2016
  2228                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2229                              <1> 	;
  2230                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  2231                              <1> 	;
  2232                              <1> ;----------------------------------------------------------------
  2233                              <1> ; WRITE_AC_CURRENT						:
  2234                              <1> ;	THTS ROUTINE WRITES THE ATTRIBUTE AND CHARACTER		:
  2235                              <1> ;	AT THE CURRENT CURSOR POSITION				:
  2236                              <1> ; INPUT								:
  2237                              <1> ;	(AH) = CURRENT CRT MODE					:
  2238                              <1> ;	(BH) = DISPLAY PAGE					:
  2239                              <1> ;	(CX) = COUNT OF CHARACTERS TO WRITE			:
  2240                              <1> ;	(AL) = CHAR TO WRITE					:
  2241                              <1> ;	(BL) = ATTRIBUTE OF CHAR TO WRITE			:
  2242                              <1> ;	(DS) = DATA SEGMENT					:
  2243                              <1> ;	(ES) = REGEN SEGMENT					:
  2244                              <1> ; OUTPUT							:
  2245                              <1> ;	DISPLAY REGEN BUFFER UPDATED				:
  2246                              <1> ;----------------------------------------------------------------
  2247                              <1> 
  2248                              <1> 	; 08/07/2016
  2249 00002002 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7 ; 6!?
  2250 00002009 760A                <1> 	jna	short write_ac_c
  2251                              <1> 
  2252 0000200B E80F0B0000          <1> 	call	vga_write_char_attr
  2253 00002010 E941F9FFFF          <1> 	jmp     VIDEO_RETURN	
  2254                              <1> 
  2255                              <1> write_ac_c:
  2256 00002015 E834000000          <1> 	call	_write_c_current
  2257                              <1> 
  2258 0000201A 0FB6F7              <1> 	movzx	esi, bh ; video page number (0 to 7)	
  2259 0000201D 889E[83660000]      <1> 	mov	[esi+chr_attrib], bl ; color/attribute
  2260                              <1> 
  2261 00002023 E92EF9FFFF          <1>         jmp     VIDEO_RETURN
  2262                              <1> 
  2263                              <1> WRITE_C_CURRENT:
  2264                              <1> 	; 08/07/2016
  2265                              <1> 	; 26/06/2016
  2266                              <1> 	; 12/05/2016
  2267                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2268                              <1> 	;
  2269                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  2270                              <1> 	;
  2271                              <1> ;----------------------------------------------------------------
  2272                              <1> ; WRITE_C_CURRENT						:
  2273                              <1> ;	THIS ROUTINE WRITES THE CHARACTER AT			:
  2274                              <1> ;	THE CURRENT CURSOR POSITION, ATTRIBUTE UNCHANGED	:
  2275                              <1> ; INPUT								:
  2276                              <1> ;	(AH) = CURRENT CRT MODE					:
  2277                              <1> ;	(BH) = DISPLAY PAGE					:
  2278                              <1> ;	(CX) = COUNT OF CHARACTERS TO WRITE			:
  2279                              <1> ;	(AL) = CHAR TO WRITE					:
  2280                              <1> ;	(DS) = DATA SEGMENT					:
  2281                              <1> ;	(ES) = REGEN SEGMENT					:
  2282                              <1> ; OUTPUT							:
  2283                              <1> ;	DISPLAY REGEN BUFFER UPDATED				:
  2284                              <1> ;----------------------------------------------------------------
  2285                              <1> 
  2286                              <1> 	; 08/07/2016
  2287 00002028 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7 ; 6!?
  2288 0000202F 760A                <1> 	jna	short write_c_c
  2289                              <1> 
  2290 00002031 E8E90A0000          <1> 	call	vga_write_char_only
  2291 00002036 E91BF9FFFF          <1> 	jmp     VIDEO_RETURN	
  2292                              <1> 
  2293                              <1> write_c_c:
  2294                              <1> 	;and	bh, 7 ; video page number (<= 7)
  2295 0000203B 0FB6F7              <1> 	movzx	esi, bh	
  2296 0000203E 8A9E[83660000]      <1> 	mov	bl, [esi+chr_attrib]
  2297                              <1> 
  2298 00002044 E805000000          <1> 	call	_write_c_current
  2299 00002049 E908F9FFFF          <1>         jmp     VIDEO_RETURN
  2300                              <1> 
  2301                              <1> _write_c_current:  ; from 'write_tty'
  2302                              <1> 	; 18/11/2020
  2303                              <1> 	; 26/06/2016
  2304                              <1> 	; 24/06/2016
  2305                              <1> 	; 12/05/2016
  2306                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2307                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  2308                              <1> 	; 18/01/2014
  2309                              <1> 	; 04/12/2013
  2310                              <1> 	;
  2311                              <1> 	; VIDEO.ASM - 06/10/85 VIDEO DISPLAY BIOS
  2312                              <1> 
  2313                              <1> 	; 18/11/2020
  2314 0000204E 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE] ; current video mode	
  2315 00002054 80FC04              <1> 	cmp	ah, 4
  2316 00002057 720A                <1>  	jb	short p40
  2317                              <1> 	
  2318                              <1> 	;cmp	byte [CRT_MODE], 4
  2319                              <1>         ;jnb	GRAPHICS_WRITE ; 26/06/2016
  2320                              <1> 
  2321 00002059 80FC07              <1> 	cmp	ah, 7 ; TEST FOR BW CARD
  2322 0000205C 7405                <1> 	je	short p40
  2323 0000205E E996070000          <1> 	jmp	GRAPHICS_WRITE
  2324                              <1> p40:
  2325                              <1> 	; al = character
  2326                              <1> 	; bl = color/attribute
  2327                              <1> 	; bh = video page
  2328                              <1> 	; cx = count of characters to write
  2329 00002063 6652                <1> 	push	dx
  2330 00002065 88DC                <1> 	mov	ah, bl  ; color/attribute (12/05/2016)
  2331 00002067 6650                <1> 	push	ax	; save character & attribute/color
  2332 00002069 6651                <1> 	push	cx
  2333 0000206B E854FDFFFF          <1> 	call 	find_position  ; get regen location and port address
  2334 00002070 6659                <1> 	pop	cx
  2335                              <1> 	; esi = regen location
  2336                              <1> 	; dx = status port
  2337                              <1> 	;
  2338 00002072 81C600800B00        <1> 	add	esi, 0B8000h ; 30/08/2014 (crt_base) 
  2339                              <1> 	;
  2340                              <1> 	; 18/11/2020
  2341                              <1> 	; convert display mode to a zero value 
  2342                              <1> 	; for 80 column color mode
  2343                              <1> 	;mov	ah, [CRT_MODE]	
  2344                              <1> 	;sub	ah, 2
  2345                              <1> 	;shr	ah, 1
  2346                              <1> 	;jnz	short p44    ; 26/06/2016
  2347                              <1> 
  2348                              <1> 	; 18/11/2020 (TRDOS 386 v2.0.3)
  2349 00002078 30DB                <1> 	xor	bl, bl	; 0
  2350 0000207A 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 03h ; 80x25 color text
  2351 00002081 7404                <1> 	je	short p41    ; Note: Only mode 03h and mode 01h are
  2352 00002083 FEC3                <1> 	inc	bl	; 1  ;       in use by TRDOS 386 as text modes	
  2353 00002085 EB1C                <1> 	jmp	short p43    ;       (07h, 00h and 02h are redirected)			
  2354                              <1> 
  2355                              <1> 	; WAIT FOR HORIZONTAL RETRACE OR VERTICAL RETRACE IF COLOR 80
  2356                              <1> p41:
  2357 00002087 FB                  <1> 	sti		; enable interrupts first
  2358                              <1> 	; 18/11/2020
  2359 00002088 08DB                <1> 	or	bl, bl
  2360 0000208A 7518                <1> 	jnz	short p44 ; mode 01h (and mode 00h) - 40x25 color text
  2361                              <1> 	;
  2362 0000208C 3A3D[AE5E0100]      <1> 	cmp     bh, [ACTIVE_PAGE]
  2363 00002092 7510                <1> 	jne	short p44
  2364                              <1> 	; 
  2365 00002094 FA                  <1> 	cli 		; block interrupts for single loop
  2366 00002095 EC                  <1> 	in	al, dx	; get status from the adapter
  2367 00002096 A808                <1> 	test	al, RVRT ; check for vertical retrace first
  2368 00002098 7509                <1> 	jnz	short p43 ; Do fast write now if vertical retrace
  2369 0000209A A801                <1> 	test	al, RHRZ ; is horizontal retrace low
  2370 0000209C 75E9                <1> 	jnz	short p41 ; wait until it is
  2371                              <1> p42:			;  wait for either retrace high
  2372 0000209E EC                  <1> 	in	al, dx ; get status again
  2373 0000209F A809                <1> 	test	al, RVRT+RHRZ ; is horizontal or vertical retrace high
  2374 000020A1 74FB                <1> 	jz	short p42 ; wait until either retrace active
  2375                              <1> p43:	
  2376 000020A3 FB                  <1> 	sti
  2377                              <1> p44:
  2378 000020A4 668B0424            <1> 	mov	ax, [esp] ; restore the character (al) & attribute (ah)
  2379 000020A8 668906              <1> 	mov	[esi], ax
  2380                              <1> 
  2381 000020AB 6649                <1> 	dec	cx
  2382 000020AD 7404                <1> 	jz	short p45
  2383                              <1> 
  2384 000020AF 46                  <1> 	inc	esi
  2385 000020B0 46                  <1> 	inc	esi
  2386 000020B1 EBD4                <1> 	jmp	short p41
  2387                              <1> p45:	
  2388 000020B3 6658                <1> 	pop	ax
  2389 000020B5 665A                <1> 	pop	dx
  2390 000020B7 C3                  <1> 	retn
  2391                              <1> 
  2392                              <1> ; 09/07/2016
  2393                              <1> ; 26/06/2016
  2394                              <1> ; 24/06/2016
  2395                              <1> ; 12/05/2016
  2396                              <1> ; 18/01/2016
  2397                              <1> ; 16/01/2016 - TRDOS 386 (TRDOS v2.0)
  2398                              <1> ; 30/06/2015
  2399                              <1> ; 27/06/2015
  2400                              <1> ; 11/03/2015
  2401                              <1> ; 02/09/2014
  2402                              <1> ; 30/08/2014
  2403                              <1> ; VIDEO FUNCTIONS
  2404                              <1> ; (write_tty - Retro UNIX 8086 v1 - U9.ASM, 01/02/2014)
  2405                              <1> 
  2406                              <1> WRITE_TTY:
  2407                              <1> 	; 09/12/2017
  2408                              <1> 	; 09/07/2016
  2409                              <1> 	; 01/07/2016
  2410                              <1> 	; 26/06/2016
  2411                              <1> 	; 24/06/2016
  2412                              <1> 	; 13/05/2016
  2413                              <1> 	; 12/05/2016
  2414                              <1> 	; 30/01/2016
  2415                              <1> 	; 18/01/2016
  2416                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
  2417                              <1> 	; 13/08/2015
  2418                              <1> 	; 02/09/2014
  2419                              <1> 	; 30/08/2014 (Retro UNIX 386 v1 - beginning)
  2420                              <1> 	; 01/02/2014 (Retro UNIX 8086 v1 - last update)
  2421                              <1> 	; 03/12/2013 (Retro UNIX 8086 v1 - beginning)	
  2422                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX, ESI, EDI)
  2423                              <1> 	;
  2424                              <1> 	; INPUT -> AL = Character to be written
  2425                              <1> 	;	   BL = Color (Forecolor, Backcolor)
  2426                              <1> 	;	   BH = Video Page (0 to 7)
  2427                              <1> 
  2428                              <1> 	; 09/07/2016
  2429 000020B8 803D[7A660000]07    <1>         cmp     byte [CRT_MODE], 7
  2430 000020BF 760A                <1> 	jna 	short write_tty_cga
  2431                              <1> 
  2432 000020C1 E8380D0000          <1> 	call	vga_write_teletype
  2433 000020C6 E98BF8FFFF          <1> 	jmp	VIDEO_RETURN
  2434                              <1> 
  2435                              <1> write_tty_cga:
  2436                              <1> 	; 13/05/2016
  2437                              <1> 	;call	_write_tty
  2438                              <1> 	; 01/07/2016
  2439 000020CB E818000000          <1> 	call	_write_tty_m3
  2440 000020D0 E981F8FFFF          <1> 	jmp	VIDEO_RETURN
  2441                              <1> 
  2442                              <1> RVRT	equ	00001000b	; VIDEO VERTICAL RETRACE BIT
  2443                              <1> RHRZ	equ	00000001b	; VIDEO HORIZONTAL RETRACE BIT
  2444                              <1> 
  2445                              <1> ; Derived from "WRITE_TTY" procedure of IBM "pc-at" rombios source code
  2446                              <1> ; (06/10/1985), 'video.asm', INT 10H, VIDEO_IO
  2447                              <1> ;
  2448                              <1> ; 06/10/85  VIDEO DISPLAY BIOS
  2449                              <1> ;
  2450                              <1> ;--- WRITE_TTY ------------------------------------------------------------------
  2451                              <1> ;										:
  2452                              <1> ;   THIS INTERFACE PROVIDES A TELETYPE LIKE INTERFACE TO THE			:
  2453                              <1> ;   VIDEO CARDS. THE INPUT CHARACTER IS WRITTEN TO THE CURRENT			:
  2454                              <1> ;   CURSOR POSITION, AND THE CURSOR IS MOVED TO THE NEXT POSITION.		:
  2455                              <1> ;   IF THE CURSOR LEAVES THE LAST COLUMN OF THE FIELD, THE COLUMN		:
  2456                              <1> ;   IS SET TO ZERO, AND THE ROW VALUE IS INCREMENTED. IF THE ROW		:
  2457                              <1> ;   ROW VALUE LEAVES THE FIELD, THE CURSOR IS PLACED ON THE LAST ROW,		:
  2458                              <1> ;   FIRST COLUMN, AND THE ENTIRE SCREEN IS SCROLLED UP ONE LINE.		:
  2459                              <1> ;   WHEN THE SCREEN IS SCROLLED UP, THE ATTRIBUTE FOR FILLING THE		:
  2460                              <1> ;   NEWLY BLANKED LINE IS READ FROM THE CURSOR POSITION ON THE PREVIOUS		:
  2461                              <1> ;   LINE BEFORE THE SCROLL, IN CHARACTER MODE. IN GRAPHICS MODE,		:
  2462                              <1> ;   THE 0 COLOR IS USED.							:
  2463                              <1> ;   ENTRY --									:
  2464                              <1> ;     (AH) = CURRENT CRT MODE							:
  2465                              <1> ;     (AL) = CHARACTER TO BE WRITTEN						:
  2466                              <1> ;	    NOTE THAT BACK SPACE, CARRIAGE RETURN, BELL AND LINE FEED ARE	:
  2467                              <1> ;	    HANDLED AS COMMANDS RATHER THAN AS DISPLAY GRAPHICS CHARACTERS	:
  2468                              <1> ;     (BL) = FOREGROUND COLOR FOR CHAR WRITE IF CURRENTLY IN A GRAPHICS MODE	:
  2469                              <1> ;   EXIT -- 									:
  2470                              <1> ;     ALL REGISTERS SAVED							:
  2471                              <1> ;--------------------------------------------------------------------------------
  2472                              <1> 
  2473                              <1> ; 18/11/2020 (TRDOS 386 v2.0.3)
  2474                              <1> ; 09/12/2017
  2475                              <1> ; 08/07/2016
  2476                              <1> ; 26/06/2016
  2477                              <1> ; 24/06/2016
  2478                              <1> _write_tty:
  2479                              <1> 	; 13/05/2016
  2480                              <1> 	; --- 18/11/2020 ---
  2481                              <1> 	; NOTE:
  2482                              <1> 	; Only kernel calls "_write_tty" procedure...
  2483                              <1> 	; TRDOS 386 v2 kernel uses video mode 3 for displaying
  2484                              <1> 	; (some error) messages and also mainprog command interpreter
  2485                              <1> 	; (in kernel) uses "_write_tty".
  2486                              <1> 	; So, here video mode must be set to 3 if it is not 3.
  2487                              <1>  
  2488 000020D5 FA                  <1> 	cli	; disable interrupts
  2489                              <1> 	;
  2490                              <1> 	; 01/09/2014
  2491 000020D6 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3
  2492 000020DD 7409                <1> 	je	short _write_tty_m3
  2493                              <1> 	;
  2494                              <1> set_mode_3:
  2495 000020DF 53                  <1> 	push	ebx
  2496 000020E0 50                  <1> 	push	eax
  2497                              <1> 	;call	_set_mode
  2498                              <1> 	; 18/11/2020 
  2499 000020E1 E87FF8FFFF          <1> 	call	set_txt_mode  ; set video mode to 03h 
  2500 000020E6 58                  <1> 	pop	eax
  2501 000020E7 5B                  <1> 	pop	ebx
  2502                              <1> 	;
  2503                              <1> _write_tty_m3: ; 24/06/2016 (m3 -> _write_tty_m3)
  2504 000020E8 0FB6F7              <1> 	movzx 	esi, bh ; 12/05/2016
  2505 000020EB 66D1E6              <1> 	shl	si, 1
  2506 000020EE 81C6[9E5E0100]      <1> 	add	esi, CURSOR_POSN
  2507 000020F4 668B16              <1> 	mov	dx, [esi]
  2508                              <1> 	;
  2509                              <1> 	; dx now has the current cursor position
  2510                              <1> 	;
  2511 000020F7 3C0D                <1> 	cmp	al, 0Dh	; CR	; is it carriage return or control character
  2512 000020F9 763E                <1> 	jbe	short u8
  2513                              <1> 	;
  2514                              <1> 	; write the char to the screen
  2515                              <1> u0:	
  2516                              <1> 	; al = character
  2517                              <1> 	; bl = attribute/color
  2518                              <1> 	; bh = video page number (0 to 7)
  2519                              <1> 	;
  2520 000020FB 66B90100            <1> 	mov	cx, 1  ; 24/06/2016
  2521                              <1> 	; cx = count of characters to write
  2522                              <1> 	;
  2523 000020FF E84AFFFFFF          <1> 	call	_write_c_current ; 16/01/2015
  2524                              <1> 	;
  2525                              <1> 	; position the cursor for next char
  2526 00002104 FEC2                <1> 	inc	dl		; next column
  2527 00002106 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS]  ; test for column overflow 
  2528 0000210C 7565                <1>         jne     _set_cpos
  2529 0000210E B200                <1> 	mov	dl, 0		; column = 0
  2530                              <1> u10:				; (line feed found)
  2531 00002110 80FE18              <1> 	cmp	dh, 25-1 	; check for last row
  2532 00002113 7220                <1> 	jb 	short u6
  2533                              <1> 	;
  2534                              <1> 	; scroll required
  2535                              <1> u1:	
  2536                              <1> 	; SET CURSOR POSITION (04/12/2013)
  2537 00002115 E859000000          <1> 	call	_set_cpos
  2538                              <1> 	;
  2539                              <1> 	; determine value to fill with during scroll
  2540                              <1> u2:
  2541                              <1> 	; bh = video page number
  2542                              <1> 	;
  2543 0000211A E897FEFFFF          <1> 	call	_read_ac_current ; 18/01/2016
  2544                              <1> 	;
  2545                              <1> 	; al = character, ah = attribute
  2546                              <1> 	; bh = video page number
  2547                              <1> 	; 18/11/2020
  2548 0000211F 88E3                <1> 	mov	bl, ah ; color/attribute 	
  2549                              <1> u3:
  2550                              <1> 	;;mov	ax, 0601h 	; scroll one line
  2551                              <1> 	;;sub	cx, cx		; upper left corner
  2552                              <1> 	;;mov	dh, 25-1 	; lower right row
  2553                              <1> 	;;;mov	dl, [CRT_COLS]
  2554                              <1> 	;mov	dl, 80		; lower right column	
  2555                              <1> 	;;dec	dl
  2556                              <1> 	;;mov	dl, 79
  2557                              <1> 
  2558                              <1> 	;;call	scroll_up	; 04/12/2013
  2559                              <1> 	;;; 11/03/2015
  2560                              <1> 	; 02/09/2014
  2561                              <1> 	;;;mov	cx, [crt_ulc] ; Upper left corner  (0000h)
  2562                              <1> 	;;;mov	dx, [crt_lrc] ; Lower right corner (184Fh)
  2563                              <1> 	; 11/03/2015
  2564 00002121 6629C9              <1> 	sub	cx, cx
  2565                              <1> 	;mov	dx, 184Fh ; dl = 79 (column), dh = 24 (row)
  2566                              <1> 	; 18/11/2020
  2567 00002124 B618                <1> 	mov	dh, 25-1
  2568 00002126 8A15[7C660000]      <1> 	mov	dl, [CRT_COLS]
  2569 0000212C FECA                <1> 	dec	dl
  2570                              <1> 	;
  2571 0000212E B001                <1> 	mov	al, 1		; scroll 1 line up
  2572                              <1> 		; ah = attribute
  2573                              <1> 	;mov	bl, al ; 12/05/2016
  2574 00002130 E9D7FCFFFF          <1> 	jmp	_scroll_up	; 16/01/2016
  2575                              <1> ;u4:
  2576                              <1> 	;;int	10h		; video-call return
  2577                              <1> 				; scroll up the screen
  2578                              <1> 				; tty return
  2579                              <1> ;u5:
  2580                              <1> 	;retn			; return to the caller
  2581                              <1> 
  2582                              <1> u6:				; set-cursor-inc
  2583 00002135 FEC6                <1> 	inc	dh		; next row
  2584                              <1> 				; set cursor
  2585                              <1> ;u7:					
  2586                              <1> 	;;mov	ah, 02h
  2587                              <1> 	;;jmp	short u4 	; establish the new cursor
  2588                              <1> 	;call	_set_cpos
  2589                              <1> 	;jmp 	short u5
  2590 00002137 EB3A                <1> 	jmp     _set_cpos
  2591                              <1> 
  2592                              <1> 	; check for control characters
  2593                              <1> u8:
  2594 00002139 7436                <1> 	je	short u9
  2595 0000213B 3C0A                <1> 	cmp	al, 0Ah		; is it a line feed (0Ah)
  2596 0000213D 74D1                <1> 	je	short u10
  2597 0000213F 3C07                <1> 	cmp	al, 07h 	; is it a bell
  2598 00002141 747A                <1> 	je	short u11
  2599 00002143 3C08                <1> 	cmp	al, 08h		; is it a backspace
  2600                              <1> 	;jne	short u0
  2601 00002145 7422                <1> 	je	short bs	; 12/12/2013
  2602                              <1> 	; 12/12/2013 (tab stop)
  2603 00002147 3C09                <1> 	cmp	al, 09h		; is it a tab stop
  2604 00002149 75B0                <1> 	jne	short u0
  2605 0000214B 88D0                <1> 	mov	al, dl
  2606                              <1> 	;cbw
  2607 0000214D 30E4                <1> 	xor	ah, ah ; 09/12/2017
  2608 0000214F B108                <1> 	mov	cl, 8
  2609 00002151 F6F1                <1> 	div	cl
  2610 00002153 28E1                <1> 	sub	cl, ah
  2611                              <1> ts:
  2612                              <1> 	; 02/09/2014
  2613                              <1> 	; 01/09/2014
  2614                              <1> 	;mov	al, 20h
  2615                              <1> tsloop:
  2616 00002155 6651                <1> 	push	cx
  2617                              <1> 	; 18/11/2020
  2618                              <1> 	;push	ax
  2619                              <1> 	;;mov	bh, [ACTIVE_PAGE]
  2620 00002157 6653                <1> 	push	bx
  2621 00002159 B020                <1> 	mov	al, 20h ; al = space (blank) 
  2622                              <1> 			; bl = color/attribute
  2623 0000215B E888FFFFFF          <1> 	call	_write_tty_m3 ; 24/06/2016 (m3 -> _write_tty_m3)
  2624                              <1> 	; 18/11/2020
  2625 00002160 665B                <1> 	pop	bx  ; BL = color/attribute, Bh = video page 
  2626                              <1> 	;pop	ax  ; AL = character
  2627 00002162 6659                <1> 	pop	cx
  2628 00002164 FEC9                <1> 	dec	cl
  2629 00002166 75ED                <1> 	jnz	short tsloop
  2630 00002168 C3                  <1> 	retn
  2631                              <1> bs:	
  2632                              <1> 	; back space found
  2633                              <1> 
  2634 00002169 08D2                <1> 	or	dl, dl 		; is it already at start of line
  2635                              <1> 	;je	short u7 	; set_cursor
  2636 0000216B 7406                <1> 	jz	short _set_cpos
  2637 0000216D 664A                <1> 	dec	dx     		; no -- just move it back
  2638                              <1> 	;jmp	short u7
  2639 0000216F EB02                <1> 	jmp	short _set_cpos
  2640                              <1> 
  2641                              <1> 	; carriage return found
  2642                              <1> u9:
  2643 00002171 B200                <1> 	mov	dl, 0 		; move to first column
  2644                              <1> 	;jmp	short u7
  2645                              <1> 	;jmp	short _set_cpos ; 30/01/2016
  2646                              <1> 
  2647                              <1> 	; line feed found
  2648                              <1> ;u10:
  2649                              <1> ;	cmp	dh, 25-1 	; bottom of screen
  2650                              <1> ;	jne	short u6 	; no, just set the cursor
  2651                              <1> ;       jmp     u1              ; yes, scroll the screen
  2652                              <1> 
  2653                              <1> _set_cpos:
  2654                              <1> 	; 12/05/2016 - TRDOS 386 (TRDOS v2.0)
  2655                              <1> 	; 27/06/2015
  2656                              <1> 	; 01/09/2014
  2657                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  2658                              <1> 	;
  2659                              <1> 	; 04/12/2013 - 12/12/2013 (Retro UNIX 8086 v1) 
  2660                              <1> 	;
  2661                              <1> 	; VIDEO.ASM - 06/10/85  VIDEO DISPLAY BIOS
  2662                              <1> 	;
  2663                              <1> ;----------------------------------------------
  2664                              <1> ; SET_CPOS
  2665                              <1> ;	THIS ROUTINE SETS THE CURRENT CURSOR POSITION TO THE
  2666                              <1> ;	NEW X-Y VALUES PASSED
  2667                              <1> ; INPUT
  2668                              <1> ;	DX - ROW,COLUMN OF NEW CURSOR
  2669                              <1> ;	BH - DISPLAY PAGE OF CURSOR
  2670                              <1> ; OUTPUT
  2671                              <1> ;	CURSOR ID SET AT 6845 IF DISPLAY PAGE IS CURRENT DISPLAY
  2672                              <1> ;----------------------------------------------
  2673                              <1> 	;
  2674 00002173 BE[9E5E0100]        <1> 	mov	esi, CURSOR_POSN
  2675 00002178 0FB6C7              <1>         movzx   eax, bh	; BH = video page number
  2676                              <1> ;	or	al, al
  2677                              <1> ;	jz	short _set_cpos_0
  2678 0000217B D0E0                <1>         shl     al, 1   ; word offset
  2679 0000217D 01C6                <1>         add     esi, eax
  2680                              <1> ;_set_cpos_0:
  2681 0000217F 668916              <1> 	mov	[esi], dx ; save the pointer
  2682 00002182 383D[AE5E0100]      <1> 	cmp	[ACTIVE_PAGE], bh
  2683 00002188 7532                <1> 	jne	short m17
  2684                              <1> 	;call	m18	; CURSOR SET
  2685                              <1> ;m17:			; SET_CPOS_RETURN
  2686                              <1> 	; 01/09/2014
  2687                              <1> ;	retn
  2688                              <1> 		; DX  = row/column
  2689                              <1> m18:
  2690 0000218A E823FCFFFF          <1> 	call	position ; determine location in regen buffer	
  2691 0000218F 668B0D[9C5E0100]    <1> 	mov	cx, [CRT_START]
  2692 00002196 6601C1              <1> 	add	cx, ax  ; add char position in regen buffer
  2693                              <1> 			; to the start address (offset) for this page
  2694 00002199 66D1E9              <1> 	shr	cx, 1	; divide by 2 for char only count
  2695 0000219C B40E                <1> 	mov	ah, 14	; register number for cursor
  2696                              <1> 	;call	m16	; output value to the 6845	
  2697                              <1> 	;retn
  2698                              <1> 
  2699                              <1> 	;-----	THIS ROUTINE OUTPUTS THE CX REGISTER
  2700                              <1> 	;	TO THE 6845 REGISTERS NAMED IN (AH)
  2701                              <1> m16:
  2702 0000219E FA                  <1> 	cli
  2703                              <1> 	;mov	dx, [addr_6845] ; address register
  2704 0000219F 66BAD403            <1> 	mov 	dx, 03D4h ; I/O address of color card
  2705 000021A3 88E0                <1> 	mov	al, ah	; get value
  2706 000021A5 EE                  <1> 	out	dx, al	; register set
  2707 000021A6 6642                <1> 	inc	dx	; data register
  2708 000021A8 EB00                <1> 	jmp	$+2	; i/o delay
  2709 000021AA 88E8                <1> 	mov	al, ch	; data
  2710 000021AC EE                  <1> 	out	dx, al	
  2711 000021AD 664A                <1> 	dec	dx	
  2712 000021AF 88E0                <1> 	mov	al, ah
  2713 000021B1 FEC0                <1> 	inc	al	; point to other data register
  2714 000021B3 EE                  <1> 	out	dx, al	; set for second register
  2715 000021B4 6642                <1> 	inc	dx
  2716 000021B6 EB00                <1> 	jmp	$+2	; i/o delay
  2717 000021B8 88C8                <1> 	mov	al, cl	; second data value
  2718 000021BA EE                  <1> 	out	dx, al
  2719 000021BB FB                  <1> 	sti
  2720                              <1> m17:
  2721 000021BC C3                  <1> 	retn
  2722                              <1> 
  2723                              <1> beeper: 
  2724                              <1> 	; 04/08/2016
  2725                              <1> 	; 12/05/2016 - TRDOS 386 (TRDOS v2.0)
  2726                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  2727                              <1> 	; 18/01/2014
  2728                              <1> 	; 03/12/2013
  2729                              <1> 	; bell found
  2730                              <1> u11:
  2731 000021BD FB                  <1> 	sti
  2732 000021BE 3A3D[AE5E0100]      <1> 	cmp	bh, [ACTIVE_PAGE]
  2733 000021C4 7551                <1> 	jne	short u12	; Do not sound the beep 
  2734                              <1> 				; if it is not written on the active page
  2735                              <1> beeper_gfx: ; 04/08/2016
  2736 000021C6 66B93305            <1> 	mov	cx, 1331 	; divisor for 896 hz tone
  2737 000021CA B31F                <1> 	mov	bl, 31		; set count for 31/64 second for beep
  2738                              <1> 	;call	beep		; sound the pod bell
  2739                              <1> 	;jmp	short u5 	; tty_return
  2740                              <1> 	;retn
  2741                              <1> 	
  2742                              <1> TIMER	equ 	040h   		; 8254 TIMER - BASE ADDRESS
  2743                              <1> PORT_B	equ	061h		; PORT B READ/WRITE DIAGNOSTIC REGISTER
  2744                              <1> GATE2	equ	00000001b	; TIMER 2 INPUT CATE CLOCK BIT
  2745                              <1> SPK2	equ	00000010b	; SPEAKER OUTPUT DATA ENABLE BIT
  2746                              <1> 
  2747                              <1> beep:
  2748                              <1> 	; 07/02/2015
  2749                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  2750                              <1> 	; 18/01/2014
  2751                              <1> 	; 03/12/2013
  2752                              <1> 	;
  2753                              <1> 	; TEST4.ASM - 06/10/85  POST AND BIOS UTILITY ROUTINES
  2754                              <1> 	;
  2755                              <1> 	; ROUTINE TO SOUND THE BEEPER USING TIMER 2 FOR TONE
  2756                              <1> 	;
  2757                              <1> 	; ENTRY:
  2758                              <1> 	;    (BL) = DURATION COUNTER ( 1 FOR 1/64 SECOND )
  2759                              <1> 	;    (CX) = FREQUENCY DIVISOR (1193180/FREQUENCY) (1331 FOR 886 HZ)
  2760                              <1> 	; EXIT:				:
  2761                              <1> 	;    (AX),(BL),(CX) MODIFIED.
  2762                              <1> 
  2763 000021CC 9C                  <1> 	pushf  ; 18/01/2014	; save interrupt status
  2764 000021CD FA                  <1> 	cli			; block interrupts during update
  2765 000021CE B0B6                <1> 	mov	al, 10110110b	; select timer 2, lsb, msb binary
  2766 000021D0 E643                <1> 	out	TIMER+3, al 	; write timer mode register
  2767 000021D2 EB00                <1> 	jmp	$+2		; I/O delay
  2768 000021D4 88C8                <1> 	mov	al, cl		; divisor for hz (low)
  2769 000021D6 E642                <1> 	out	TIMER+2,AL	; write timer 2 count - lsb
  2770 000021D8 EB00                <1> 	jmp	$+2		; I/O delay
  2771 000021DA 88E8                <1> 	mov	al, ch		; divisor for hz (high)
  2772 000021DC E642                <1> 	out	TIMER+2, al	; write timer 2 count - msb
  2773 000021DE E461                <1> 	in	al, PORT_B	; get current setting of port
  2774 000021E0 88C4                <1> 	mov	ah, al		; save that setting
  2775 000021E2 0C03                <1> 	or	al, GATE2+SPK2	; gate timer 2 and turn speaker on
  2776 000021E4 E661                <1> 	out	PORT_B, al	; and restore interrupt status
  2777                              <1> 	;popf	; 18/01/2014
  2778 000021E6 FB                  <1> 	sti
  2779                              <1> g7:				; 1/64 second per count (bl)
  2780 000021E7 B90B040000          <1> 	mov	ecx, 1035	; delay count for 1/64 of a second	
  2781 000021EC E827000000          <1> 	call	waitf		; go to beep delay 1/64 count
  2782 000021F1 FECB                <1> 	dec	bl		; (bl) length count expired?
  2783 000021F3 75F2                <1> 	jnz	short g7	; no - continue beeping speaker
  2784                              <1> 	;
  2785                              <1> 	;pushf			; save interrupt status
  2786 000021F5 FA                  <1> 	cli  	; 18/01/2014	; block interrupts during update
  2787 000021F6 E461                <1> 	in	al, PORT_B	; get current port value
  2788                              <1>         ;or      al, not (GATE2+SPK2) ; isolate current speaker bits in case
  2789 000021F8 0CFC                <1>         or      al, ~(GATE2+SPK2)
  2790 000021FA 20C4                <1>         and	ah, al		; someone turned them off during beep
  2791 000021FC 88E0                <1> 	mov	al, ah		; recover value of port
  2792                              <1>         ;or      al, not (GATE2+SPK2) ; force speaker data off
  2793 000021FE 0CFC                <1> 	or 	al, ~(GATE2+SPK2) ; isolate current speaker bits in case
  2794 00002200 E661                <1> 	out	PORT_B, al	; and stop speaker timer
  2795                              <1> 	;popf			; restore interrupt flag state
  2796 00002202 FB                  <1> 	sti
  2797 00002203 B90B040000          <1> 	mov	ecx, 1035	; force 1/64 second delay (short)
  2798 00002208 E80B000000          <1> 	call	waitf		; minimum delay between all beeps
  2799                              <1> 	;pushf			; save interrupt status
  2800 0000220D FA                  <1> 	cli			; block interrupts during update
  2801 0000220E E461                <1> 	in	al, PORT_B	; get current port value in case	
  2802 00002210 2403                <1> 	and	al, GATE2+SPK2	; someone turned them on
  2803 00002212 08E0                <1> 	or	al, ah		; recover value of port_b
  2804 00002214 E661                <1> 	out	PORT_B, al	; restore speaker status
  2805 00002216 9D                  <1> 	popf			; restore interrupt flag state
  2806                              <1> u12:	
  2807 00002217 C3                  <1> 	retn
  2808                              <1> 
  2809                              <1> REFRESH_BIT equ	00010000b 	; REFRESH TEST BIT
  2810                              <1> 
  2811                              <1> WAITF:
  2812                              <1> waitf:
  2813                              <1> 	; 30/08/2014 (Retro UNIX 386 v1)
  2814                              <1> 	; 03/12/2013
  2815                              <1> 	;
  2816                              <1> ;	push ax			; save work register (ah)	
  2817                              <1> ;waitf1:
  2818                              <1> 				; use timer 1 output bits
  2819                              <1> ;	in	al, PORT_B	; read current counter output status
  2820                              <1> ;	and	al, REFRESH_BIT	; mask for refresh determine bit
  2821                              <1> ;	cmp	al, ah		; did it just change
  2822                              <1> ;	je	short waitf1	; wait for a change in output line
  2823                              <1> ;	;
  2824                              <1> ;	mov	ah, al		; save new lflag state
  2825                              <1> ;	loop	waitf1		; decrement half cycles till count end		
  2826                              <1> ;	;
  2827                              <1> ;	pop	ax		; restore (ah)
  2828                              <1> ;	retn			; return (cx)=0
  2829                              <1> 
  2830                              <1> ; 06/02/2015 (unix386.s <-- dsectrm2.s)
  2831                              <1> ; 17/12/2014 (dsectrm2.s)
  2832                              <1> ; WAITF
  2833                              <1> ; /// IBM PC-XT Model 286 System BIOS Source Code - Test 4 - 06/10/85 ///
  2834                              <1> ;
  2835                              <1> ;---WAITF-----------------------------------------------------------------------
  2836                              <1> ;	FIXED TIME WAIT ROUTINE (HARDWARE CONTROLLED - NOT PROCESSOR)
  2837                              <1> ; ENTRY:
  2838                              <1> ;	(CX) =	COUNT OF 15.085737 MICROSECOND INTERVALS TO WAIT
  2839                              <1> ;	      	MEMORY REFRESH TIMER 1 OUTPUT USED AS REFERENCE
  2840                              <1> ; EXIT:
  2841                              <1> ;	       	AFTER (CX) TIME COUNT (PLUS OR MINUS 16 MICROSECONDS)
  2842                              <1> ;	(CX) = 0	
  2843                              <1> ;-------------------------------------------------------------------------------
  2844                              <1> 
  2845                              <1> ; Refresh period: 30 micro seconds (15-80 us)
  2846                              <1> ; (16/12/2014 - AWARDBIOS 1999 - ATORGS.ASM, WAIT_REFRESH)
  2847                              <1> 
  2848                              <1> ;WAITF:					; DELAY FOR (CX)*15.085737 US
  2849 00002218 6650                <1> 	PUSH	AX			; SAVE WORK REGISTER (AH)
  2850                              <1> 	; 16/12/2014
  2851                              <1> 	;shr	cx, 1			; convert to count of 30 micro seconds
  2852 0000221A D1E9                <1> 	shr	ecx, 1	; 21/02/2015
  2853                              <1> ;17/12/2014	
  2854                              <1> ;WAITF1:
  2855                              <1> ;	IN	AL, PORT_B   ;061h	; READ CURRENT COUNTER OUTPUT STATUS
  2856                              <1> ;	AND	AL, REFRESH_BIT	;00010000b ; MASK FOR REFRESH DETERMINE BIT
  2857                              <1> ;	CMP	AL, AH			; DID IT JUST CHANGE
  2858                              <1> ;	JE	short WAITF1		; WAIT FOR A CHANGE IN OUTPUT LINE
  2859                              <1> ;	MOV	AH, AL			; SAVE NEW FLAG STATE
  2860                              <1> ;	LOOP	WAITF1			; DECREMENT HALF CYCLES TILL COUNT END		
  2861                              <1> 	;
  2862                              <1> 	; 17/12/2014
  2863                              <1> 	;
  2864                              <1> 	; Modification from 'WAIT_REFRESH' procedure of AWARD BIOS - 1999
  2865                              <1> 	;
  2866                              <1> ;WAIT_REFRESH:  Uses port 61, bit 4 to have CPU speed independent waiting.
  2867                              <1> ;   	INPUT:  CX = number of refresh periods to wait
  2868                              <1> ;     	       (refresh periods = 1 per 30 microseconds on most machines)
  2869                              <1> WR_STATE_0:
  2870 0000221C E461                <1> 	IN	AL,PORT_B		; IN AL,SYS1
  2871 0000221E A810                <1> 	TEST	AL,010H
  2872 00002220 74FA                <1> 	JZ	SHORT WR_STATE_0
  2873                              <1> WR_STATE_1:
  2874 00002222 E461                <1> 	IN	AL,PORT_B		; IN AL,SYS1
  2875 00002224 A810                <1> 	TEST	AL,010H
  2876 00002226 75FA                <1> 	JNZ	SHORT WR_STATE_1
  2877 00002228 E2F2                <1>         LOOP    WR_STATE_0
  2878                              <1> 	;
  2879 0000222A 6658                <1> 	POP	AX			; RESTORE (AH)
  2880 0000222C C3                  <1> 	RETn				; (CX) = 0
  2881                              <1> 
  2882                              <1> ; 09/07/2016
  2883                              <1> ; 01/07/2016
  2884                              <1> ; 24/06/2016
  2885                              <1> ; 23/06/2016 - TRDOS 386 (TRDOS v2.0)
  2886                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  2887                              <1> ;-------------------------------------------------------------------------------
  2888                              <1> ; WRITE_STRING								       :
  2889                              <1> ;	THIS ROUTINE WRITES A STRING OF CHARACTERS TO THE CRT.		       :
  2890                              <1> ; INPUT 								       :
  2891                              <1> ;	(AL) = WRITE STRING COMMAND  0 - 3				       :
  2892                              <1> ;	(BH) = DISPLAY PAGE (ACTIVE PAGE)				       :
  2893                              <1> ;	(CX) = COUNT OF CHARACTERS TO WRITE, IF (CX) = 0 THEN RETURN	       :
  2894                              <1> ;	(DX) = CURSOR POSITION FOR START OF STRING WRITE		       :
  2895                              <1> ;	(BL) = ATTRIBUTE OF CHARACTER TO WRITE IF (AL) = 0  OR	(AL) = 1       :
  2896                              <1> ;	(eBP) = SOURCE STRING OFFSET					       :
  2897                              <1> ; OUTPUT								       :
  2898                              <1> ;	NONE								       :
  2899                              <1> ;-------------------------------------------------------------------------------
  2900                              <1> 
  2901                              <1> ; AL = 00h: Assign all characters the attribute in BL; do not update cursor
  2902                              <1> ; AL = 01h: Assign all characters the attribute in BL; update cursor
  2903                              <1> ; AL = 02h: Use attributes in string; do not update cursor
  2904                              <1> ; AL = 03h: Use attributes in string; update cursor
  2905                              <1> 
  2906                              <1> WRITE_STRING:
  2907                              <1> 	; 12/09/2016
  2908                              <1> 	; 09/07/2016
  2909                              <1> 	;cmp	byte [CRT_MODE], 7 ; 6?!
  2910                              <1> 	;ja	VIDEO_RETURN		; not a valid function for VGA modes
  2911                              <1> 	;
  2912 0000222D A2[146B0100]        <1> 	mov	[w_str_cmd], al		; save (AL) command
  2913 00002232 3C04                <1> 	CMP	AL, 4			; TEST FOR INVALID WRITE STRING OPTION
  2914 00002234 0F831CF7FFFF        <1> 	JNB	VIDEO_RETURN		; IF OPTION INVALID THEN RETURN
  2915                              <1> 
  2916                              <1>         ;JCXZ   VIDEO_RETURN            ; IF ZERO LENGTH STRING THEN RETURN
  2917                              <1> 
  2918 0000223A 67E362              <1>         jcxz    P55			; 01/07/2016
  2919                              <1> 
  2920                              <1> 	; 01/07/2016
  2921                              <1> 	;and	ecx, 0FFFFh
  2922                              <1> 	; ECX = byte count
  2923                              <1> 	;push	ecx
  2924 0000223D 89EE                <1> 	mov	esi, ebp ; user buffer
  2925 0000223F BF00000700          <1> 	mov	edi, Cluster_Buffer  ; system buffer
  2926 00002244 E863CB0000          <1> 	call	transfer_from_user_buffer
  2927                              <1> 	;pop	ecx
  2928 00002249 0F8207F7FFFF        <1> 	jc	VIDEO_RETURN
  2929                              <1> 	; ecx = transfer (byte) count = character count
  2930 0000224F BD00000700          <1> 	mov	ebp, Cluster_Buffer
  2931                              <1> 	; 12/09/2016
  2932 00002254 803D[7A660000]07    <1> 	cmp	byte [CRT_MODE], 7 ; 6?!
  2933 0000225B 0F87A5000000        <1> 	ja	vga_write_string
  2934                              <1> 	;
  2935 00002261 0FB6F7              <1> 	movzx	esi, bh			; GET CURRENT CURSOR PAGE
  2936 00002264 66D1E6              <1> 	SAL	SI, 1			; CONVERT TO PAGE OFFSET  (SI= PAGE)
  2937                              <1> 	; *****
  2938 00002267 66FFB6[9E5E0100]    <1> 	PUSH	word [eSI+CURSOR_POSN]	; SAVE CURRENT CURSOR POSITION IN STACK
  2939                              <1> 
  2940                              <1> 	;MOV	AX,0200H		; SET NEW CURSOR POSITION
  2941                              <1> 	;INT	10H
  2942                              <1> P50next:	
  2943 0000226E 51                  <1> 	push	ecx ; ****
  2944 0000226F 53                  <1> 	push	ebx ; *** ; 18/11/2020
  2945 00002270 56                  <1> 	push	esi ; **
  2946 00002271 52                  <1> 	push	edx ; *
  2947 00002272 E8FCFEFFFF          <1> 	call	_set_cpos
  2948                              <1> P50:
  2949 00002277 8A4500              <1> 	MOV	AL, [eBP]		; GET CHARACTER FROM INPUT STRING
  2950 0000227A 45                  <1> 	INC	eBP			; BUMP POINTER TO CHARACTER
  2951                              <1> 
  2952                              <1> ;-----	TEST FOR SPECIAL CHARACTER'S
  2953                              <1> 
  2954 0000227B 3C08                <1> 	CMP	AL, 08H			; IS IT A BACKSPACE
  2955 0000227D 7410                <1> 	JE	short P51		; BACK_SPACE
  2956 0000227F 3C0D                <1> 	CMP	AL, 0Dh ; CR		; IS IT CARRIAGE RETURN
  2957 00002281 740C                <1> 	JE	short P51		; CAR_RET
  2958 00002283 3C0A                <1> 	CMP	AL, 0Ah ; LF		; IS IT A LINE FEED
  2959 00002285 7408                <1> 	JE	short P51		; LINE_FEED
  2960                              <1> 	; 18/11/2020
  2961 00002287 3C09                <1> 	cmp	al, 09h			; is it a tab stop
  2962 00002289 7404                <1> 	je	short P51
  2963                              <1> 	;
  2964 0000228B 3C07                <1> 	CMP	AL, 07h			; IS IT A BELL
  2965 0000228D 7515                <1> 	JNE	short P52		; IF NOT THEN DO WRITE CHARACTER
  2966                              <1> P51:
  2967                              <1> 	;MOV	AH,0EH			; TTY_CHARACTER_WRITE
  2968                              <1> 	;INT	10H			; WRITE TTY CHARACTER TO THE CRT
  2969                              <1> 	
  2970 0000228F E854FEFFFF          <1> 	call	_write_tty_m3
  2971                              <1> 
  2972 00002294 5A                  <1> 	pop	edx ; *
  2973 00002295 5E                  <1> 	pop	esi ; **
  2974                              <1> 
  2975 00002296 668B96[9E5E0100]    <1> 	MOV	DX, [eSI+CURSOR_POSN]	; GET CURRENT CURSOR POSITION
  2976 0000229D EB48                <1> 	JMP	SHORT P54		; SET CURSOR POSITION AND CONTINUE
  2977                              <1> P55:
  2978 0000229F E9B2F6FFFF          <1> 	JMP	VIDEO_RETURN
  2979                              <1> P52:
  2980 000022A4 66B90100            <1> 	MOV	CX, 1			; SET CHARACTER WRITE AMOUNT TO ONE
  2981 000022A8 803D[146B0100]02    <1> 	CMP	byte [w_str_cmd], 2	; IS THE ATTRIBUTE IN THE STRING
  2982 000022AF 7204                <1> 	JB	short P53		; IF NOT THEN SKIP
  2983 000022B1 8A5D00              <1> 	MOV	BL, [eBP]		; ELSE GET NEW ATTRIBUTE
  2984 000022B4 45                  <1> 	INC	eBP			; BUMP STRING POINTER
  2985                              <1> P53:
  2986                              <1> 	;MOV	AH,09H			; GOT_CHARACTER
  2987                              <1> 	;INT	10H			; WRITE CHARACTER TO THE CRT
  2988                              <1> 
  2989 000022B5 E894FDFFFF          <1> 	call	_write_c_current
  2990                              <1> 	
  2991 000022BA 5A                  <1> 	pop	edx ; *	
  2992                              <1> 	; 18/11/2020
  2993 000022BB 8B5C2404            <1> 	mov	ebx, [esp+4]	; ***
  2994                              <1> 
  2995 000022BF 0FB6F7              <1> 	movzx	esi, bh ; video page number (0 to 7)	
  2996 000022C2 889E[83660000]      <1> 	mov	[esi+chr_attrib], bl ; color/attribute
  2997                              <1> 
  2998 000022C8 FEC2                <1> 	INC	DL			; INCREMENT COLUMN COUNTER
  2999 000022CA 3A15[7C660000]      <1> 	CMP	DL, [CRT_COLS]		; IF COLS ARE WITHIN RANGE FOR THIS MODE
  3000 000022D0 7215                <1> 	JB	short P54		;    THEN GO TO COLUMNS SET
  3001 000022D2 FEC6                <1> 	INC	DH			; BUMP ROW COUNTER BY ONE
  3002 000022D4 28D2                <1> 	SUB	DL, DL			; SET COLUMN COUNTER TO ZERO
  3003 000022D6 80FE19              <1> 	CMP	DH, 25			; IF ROWS ARE LESS THAN 25 THEN
  3004 000022D9 720C                <1> 	JB	short P54		; GO TO ROWS_COLUMNS_SET
  3005                              <1> 
  3006                              <1> 	; 18/11/2020
  3007                              <1> 	;MOV	AX,0E0AH		; ELSE SCROLL SCREEN
  3008                              <1> 	;INT	10H			; RESET ROW COUNTER TO 24
  3009                              <1> 
  3010                              <1> 	; 18/11/2020
  3011 000022DB B00A                <1> 	mov	al, 0Ah	; line feed
  3012                              <1> 
  3013 000022DD E806FEFFFF          <1> 	call	_write_tty_m3
  3014                              <1> 	
  3015 000022E2 66BA0018            <1> 	mov	dx, 1800h		; Column = 0, Row = 24
  3016                              <1> 	; 18/11/2020
  3017 000022E6 5E                  <1> 	pop	esi ; **
  3018                              <1> P54:					; ROW_COLUMNS_SET
  3019                              <1> 	;MOV	AX,0200H		; SET NEW CURSOR POSITION COMMAND
  3020                              <1> 	;INT	10H			; ESTABLISH NEW CURSOR POSITION
  3021                              <1> 
  3022                              <1> 	; 18/11/2020
  3023 000022E7 5B                  <1> 	pop	ebx ; ***
  3024 000022E8 59                  <1> 	pop	ecx ; ****
  3025                              <1> 
  3026                              <1> 	;LOOP	P50			; DO IT ONCE MORE UNTIL (CX) = ZERO
  3027 000022E9 6649                <1> 	dec	cx
  3028 000022EB 7581                <1> 	jnz	short P50next
  3029                              <1> 
  3030 000022ED 665A                <1> 	POP	DX  ; *****		; RESTORE OLD CURSOR COORDINATES
  3031                              <1> 	
  3032 000022EF F605[146B0100]01    <1> 	test	byte [w_str_cmd], 1	; IF CURSOR WAS NOT TO BE MOVED
  3033 000022F6 0F855AF6FFFF        <1> 	JNZ	VIDEO_RETURN		; THEN EXIT WITHOUT RESETTING OLD VALUE
  3034                              <1> 	
  3035                              <1> 	;MOV	AX,0200H		; ELSE RESTORE OLD CURSOR POSITION
  3036                              <1> 	;INT	10H
  3037                              <1> 					; DONE - EXIT WRITE STRING
  3038 000022FC E872FEFFFF          <1> 	call	_set_cpos
  3039 00002301 E950F6FFFF          <1> 	JMP	VIDEO_RETURN		; RETURN TO CALLER
  3040                              <1> 
  3041                              <1> vga_write_string:
  3042                              <1> 	; 12/09/2016 - TRDOS 386 (TRDOS v2.0)
  3043                              <1> 	;
  3044                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3045                              <1> 	; vgabios-0.7a (2011)
  3046                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3047                              <1> 	; 'vgabios.c', ' biosfn_write_string'
  3048                              <1> 
  3049                              <1> 	; INPUT 								  :
  3050                              <1> 	;	(AL) = WRITE STRING COMMAND  0 - 3				  :
  3051                              <1> 	;	(BH) = DISPLAY PAGE (ACTIVE PAGE)				  :
  3052                              <1> 	;	(CX) = COUNT OF CHARACTERS TO WRITE, IF (CX) = 0 THEN RETURN	  :
  3053                              <1> 	;	(DX) = CURSOR POSITION FOR START OF STRING WRITE		  :
  3054                              <1> 	;	(BL) = ATTRIBUTE OF CHARACTER TO WRITE IF (AL) = 0  OR	(AL) = 1  :
  3055                              <1> 	;	(eBP) = SOURCE STRING OFFSET					  :
  3056                              <1> 	; OUTPUT								  :
  3057                              <1> 	;	NONE								  :
  3058                              <1> 	;-------------------------------------------------------------------------;
  3059                              <1> 
  3060                              <1> 	; AL = 00h: Assign all characters the attribute in BL; do not update cursor
  3061                              <1> 	; AL = 01h: Assign all characters the attribute in BL; update cursor
  3062                              <1> 	; AL = 02h: Use attributes in string; do not update cursor
  3063                              <1> 	; AL = 03h: Use attributes in string; update cursor
  3064                              <1> 	
  3065                              <1> 	; biosfn_write_string(GET_AL(),GET_BH(),GET_BL(),CX,GET_DH(),GET_DL(),ES,BP);
  3066                              <1> 	; static void biosfn_write_string (flag,page,attr,count,row,col,seg,offset) 
  3067                              <1> 
  3068                              <1> 	; // Read curs info for the page
  3069                              <1>  	; biosfn_get_cursor_pos(page,&dummy,&oldcurs);
  3070                              <1> 	; bh = video page = 0
  3071                              <1> 	;movzx	esi, word [CURSOR_POSN] ; current cursor position for video page 0
  3072                              <1> 	
  3073                              <1> 	; // if row=0xff special case : use current cursor position
  3074                              <1> 	; if(row==0xff)
  3075                              <1> 	;  {col=oldcurs&0x00ff;
  3076                              <1> 	;   row=(oldcurs&0xff00)>>8;
  3077                              <1> 	;  }
  3078                              <1> 
  3079                              <1> 	;mov	al, [w_str_cmd]
  3080                              <1> 
  3081 00002306 80FEFF              <1> 	cmp	dh, 0FFh
  3082 00002309 7407                <1> 	je	short vga_wstr_1 ; user current cursor position
  3083                              <1> vga_wstr_0:
  3084                              <1> 	; set cursor position
  3085 0000230B 668915[9E5E0100]    <1> 	mov	[CURSOR_POSN], dx ; save cursor pos for pg 0
  3086                              <1> vga_wstr_1:
  3087 00002312 66FF35[9E5E0100]    <1> 	push	word [CURSOR_POSN] ; *
  3088                              <1> 
  3089                              <1> 	; ebp = string offset in system buffer (user buffer was copied to)	
  3090                              <1> 	
  3091                              <1> 	; while(count--!=0)
  3092                              <1> 	;  {
  3093                              <1> 	;   car=read_byte(seg,offset++);
  3094                              <1> 	;   if((flag&0x02)!=0)
  3095                              <1> 	;    attr=read_byte(seg,offset++);
  3096                              <1> 	;    biosfn_write_teletype(car,page,attr,WITH_ATTR);
  3097                              <1> 	;  }
  3098                              <1> 
  3099                              <1> 	;push	eax ; **
  3100                              <1> 	;test	al, 2
  3101 00002319 F605[146B0100]02    <1> 	test	byte [w_str_cmd], 2
  3102 00002320 751D                <1> 	jnz	short vga_wstr_3
  3103 00002322 881D[AF5E0100]      <1> 	mov	[ccolor], bl
  3104                              <1> vga_wstr_2:
  3105 00002328 51                  <1> 	push	ecx
  3106 00002329 8A4500              <1> 	mov	al, [ebp]
  3107 0000232C E8CD0A0000          <1> 	call	vga_write_teletype
  3108 00002331 59                  <1> 	pop	ecx
  3109 00002332 6649                <1> 	dec	cx
  3110 00002334 741E                <1> 	jz	short vga_wstr_4
  3111 00002336 45                  <1> 	inc	ebp
  3112 00002337 8A1D[AF5E0100]      <1> 	mov	bl, [ccolor]
  3113 0000233D EBE9                <1> 	jmp	short vga_wstr_2
  3114                              <1> vga_wstr_3:
  3115 0000233F 51                  <1> 	push	ecx
  3116 00002340 8A4500              <1> 	mov	al, [ebp]
  3117 00002343 45                  <1> 	inc	ebp
  3118 00002344 8A5D00              <1> 	mov	bl, [ebp]
  3119 00002347 E8B20A0000          <1> 	call	vga_write_teletype
  3120 0000234C 59                  <1> 	pop	ecx
  3121 0000234D 6649                <1> 	dec	cx
  3122 0000234F 7403                <1> 	jz	short vga_wstr_4
  3123 00002351 45                  <1> 	inc	ebp
  3124 00002352 EBEB                <1> 	jmp	short vga_wstr_3
  3125                              <1> vga_wstr_4:
  3126                              <1> 	; // Set back curs pos 
  3127                              <1> 	; if((flag&0x01)==0)
  3128                              <1> 	;  biosfn_set_cursor_pos(page,oldcurs);
  3129                              <1> 	; }
  3130                              <1> 	;pop	eax ; **
  3131 00002354 665A                <1> 	pop	dx ; word [CURSOR_POSN] ; *
  3132                              <1> 	;test	al, 1
  3133 00002356 F605[146B0100]01    <1> 	test	byte [w_str_cmd], 1
  3134 0000235D 0F85F3F5FFFF        <1> 	jnz	VIDEO_RETURN
  3135 00002363 668915[9E5E0100]    <1> 	mov 	[CURSOR_POSN], dx
  3136 0000236A E9E7F5FFFF          <1> 	JMP	VIDEO_RETURN
  3137                              <1> 
  3138                              <1> ; 07/07/2016
  3139                              <1> ; 27/06/2016 - TRDOS 386 (TRDOS v2.0)
  3140                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  3141                              <1> ;------------------------------------------------------
  3142                              <1> ;  SCROLL UP
  3143                              <1> ;   THIS ROUTINE SCROLLS UP THE INFORMATION ON THE CRT
  3144                              <1> ; ENTRY ---
  3145                              <1> ;  CH,CL = UPPER LEFT CORNER OF REGION TO SCROLL
  3146                              <1> ;  DH,DL = LOWER RIGHT CORNER OF REGION TO SCROLL
  3147                              <1> ;   BOTH OF THE ABOVE ARE IN CHARACTER POSITIONS
  3148                              <1> ;  BH = FILL VALUE FOR BLANKED LINES
  3149                              <1> ;  AL = # LINES TO SCROLL (AL=0 MEANS BLANK THE ENTIRE FIELD)
  3150                              <1> ;  DS = DATA SEGMENT
  3151                              <1> ;  ES = REGEN SEGMENT
  3152                              <1> ; EXIT --
  3153                              <1> ;  NOTHING, THE SCREEN IS SCROLLED
  3154                              <1> ;--------------------------------------------------------
  3155                              <1> 
  3156                              <1> 	; cl = upper left column
  3157                              <1> 	; ch = upper left row
  3158                              <1> 	; dl = lower rigth column
  3159                              <1> 	; dh = lower right row
  3160                              <1> 	;
  3161                              <1> 	; al = line count (AL=0 means blank entire fields)
  3162                              <1> 	; bl = fill value for blanked lines	
  3163                              <1> 	; bh = unused
  3164                              <1> 
  3165                              <1> GRAPHICS_UP:
  3166                              <1> 	; 07/07/2016
  3167                              <1> 	;AH = Current video mode, [CRT_MODE]
  3168 0000236F 80FC07              <1> 	cmp	ah, 7
  3169 00002372 7766                <1> 	ja	short vga_graphics_up
  3170                              <1> 	;je	n0
  3171                              <1> 
  3172 00002374 88C7                <1> 	MOV	bh, al			; save line count in BH
  3173 00002376 6689C8              <1> 	MOV	AX, CX			; GET UPPER LEFT POSITION INTO AX REG
  3174                              <1> 
  3175                              <1> ;-----	USE CHARACTER SUBROUTINE FOR POSITIONING
  3176                              <1> ;-----	ADDRESS RETURNED IS MULTIPLIED BY 2 FROM CORRECT VALUE
  3177                              <1> 
  3178 00002379 E8DA050000          <1> 	CALL	GRAPH_POSN
  3179 0000237E 0FB7F8              <1> 	MOVzx	eDI, AX			; SAVE RESULT AS DESTINATION ADDRESS
  3180                              <1> 
  3181                              <1> ;-----	DETERMINE SIZE OF WINDOW
  3182                              <1> 
  3183 00002381 6629CA              <1> 	SUB	DX, CX
  3184 00002384 6681C20101          <1>         ADD     DX, 101h                ; ADJUST VALUES
  3185 00002389 C0E602              <1> 	SAL	DH, 2			; MULTIPLY ROWS BY 4 AT 8 VERT DOTS/CHAR
  3186                              <1> 					; AND EVEN/ODD ROWS
  3187                              <1> ;-----	DETERMINE CRT MODE
  3188                              <1> 
  3189 0000238C 803D[7A660000]06    <1> 	CMP	byte [CRT_MODE], 6	; TEST FOR MEDIUM RES
  3190 00002393 7305                <1>         JNC     short _R7_              ; FIND_SOURCE
  3191                              <1> 
  3192                              <1> ;-----	MEDIUM RES UP
  3193 00002395 D0E2                <1> 	SAL	DL, 1			; # COLUMNS * 2, SINCE 2 BYTES/CHAR
  3194 00002397 66D1E7              <1> 	SAL	DI, 1			; OFFSET *2 SINCE 2 BYTES/CHAR
  3195                              <1> 
  3196                              <1> ;-----	DETERMINE THE SOURCE ADDRESS IN THE BUFFER
  3197                              <1> _R7_:                                   ; FIND_SOURCE
  3198 0000239A 81C700800B00        <1> 	add	edi, 0B8000h
  3199 000023A0 C0E702              <1> 	sal	bh, 2			; multiply number of lines by 4
  3200 000023A3 7431                <1>         JZ      short _R11              ; IF ZERO, THEN BLANK ENTIRE FIELD
  3201 000023A5 B050                <1> 	MOV	AL, 80			; 80 BYTES/ROW
  3202 000023A7 F6E7                <1> 	mul	bh			; determine offset to source
  3203 000023A9 0FB7F0              <1> 	movzx	esi, ax			; offset to source
  3204 000023AC 01FE                <1> 	add	eSI, eDI		; SET UP SOURCE
  3205 000023AE 88F4                <1> 	MOV	AH, DH			; NUMBER OF ROWS IN FIELD
  3206 000023B0 28FC                <1> 	sub	ah, bh			; determine number to move
  3207                              <1> 
  3208                              <1> ;-----	LOOP THROUGH, MOVING ONE ROW AT A TIME, BOTH EVEN AND ODD FIELDS
  3209                              <1> _R8:                                    ; ROW_LOOP
  3210 000023B2 E813040000          <1>         CALL    _R17                    ; MOVE ONE ROW
  3211 000023B7 6681EEB01F          <1> 	SUB	SI, 2000h-80		; MOVE TO NEXT ROW
  3212 000023BC 6681EFB01F          <1> 	SUB	DI, 2000h-80
  3213 000023C1 FECC                <1> 	DEC	AH			; NUMBER OF ROWS TO MOVE
  3214 000023C3 75ED                <1>         JNZ     short _R8               ; CONTINUE TILL ALL MOVED
  3215                              <1> 
  3216                              <1> ;-----	FILL IN THE VACATED LINE(S)
  3217                              <1> _R9:                                    ; CLEAR ENTRY
  3218 000023C5 88D8                <1> 	mov	al, bl			; attribute to fill with
  3219                              <1> _R10_:
  3220 000023C7 E81A040000          <1>         CALL    _R18                    ; CLEAR THAT ROW
  3221 000023CC 6681EFB01F          <1> 	SUB	DI, 2000h-80		; POINT TO NEXT LINE
  3222 000023D1 FECF                <1> 	dec	bh			; number of lines to fill
  3223 000023D3 75F2                <1>         JNZ     short _R10_             ; CLEAR LOOP
  3224 000023D5 C3                  <1> 	retn				; EVERYYHING DONE
  3225                              <1> 
  3226                              <1> _R11:                                   ; BLANK_FIELD
  3227 000023D6 88F7                <1> 	mov	bh, dh			; set blank count to everything in field
  3228 000023D8 EBEB                <1>         JMP     short _R9               ; CLEAR THE FIELD
  3229                              <1> 
  3230                              <1> vga_graphics_up:
  3231                              <1> 	; 08/08/2016
  3232                              <1> 	; 07/08/2016
  3233                              <1> 	; 04/08/2016
  3234                              <1> 	; 01/08/2016
  3235                              <1> 	; 31/07/2016
  3236                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3237                              <1> 	;
  3238                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3239                              <1> 	; vgabios-0.7a (2011)
  3240                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3241                              <1> 	; 'vgabios.c', 'biosfn_scroll'
  3242                              <1> 	;
  3243                              <1> 
  3244                              <1> 	; cl = upper left column
  3245                              <1> 	; ch = upper left row
  3246                              <1> 	; dl = lower rigth column
  3247                              <1> 	; dh = lower right row
  3248                              <1> 	;
  3249                              <1> 	; al = line count (AL=0 means blank entire fields)
  3250                              <1> 	; bl = fill value for blanked lines	
  3251                              <1> 	; bh = unused
  3252                              <1> 	;
  3253                              <1> 	; ah = [CRT_MODE], current video mode	
  3254                              <1> 
  3255 000023DA 88C7                <1> 	mov	bh, al ; 31/07/2016
  3256 000023DC BE[9E660000]        <1> 	mov	esi, vga_g_modes
  3257 000023E1 89F7                <1> 	mov	edi, esi
  3258 000023E3 83C708              <1> 	add	edi, vga_g_mode_count
  3259                              <1> vga_g_up_0:
  3260 000023E6 AC                  <1> 	lodsb
  3261 000023E7 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  3262 000023E9 7405                <1> 	je	short vga_g_up_1
  3263 000023EB 39FE                <1> 	cmp	esi, edi
  3264 000023ED 72F7                <1> 	jb	short vga_g_up_0
  3265                              <1> 	;xor	bh, bh ; 31/07/2016)
  3266 000023EF C3                  <1> 	retn	; nothing to do
  3267                              <1> vga_g_up_1:
  3268 000023F0 88F8                <1> 	mov	al, bh ; 31/07/2016
  3269 000023F2 83C64F              <1> 	add	esi, vga_g_memmodel - (vga_g_modes + 1)  
  3270                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  3271                              <1> 	
  3272                              <1> 	; if(rlr>=nbrows)rlr=nbrows-1;
  3273                              <1>  	; if(clr>=nbcols)clr=nbcols-1;
  3274                              <1>  	; if(nblines>nbrows)nblines=0;
  3275                              <1>  	; cols=clr-cul+1;
  3276                              <1> 
  3277 000023F5 3A35[82660000]      <1> 	cmp	dh, [VGA_ROWS]
  3278 000023FB 7208                <1> 	jb	short vga_g_up_2
  3279 000023FD 8A35[82660000]      <1> 	mov	dh, [VGA_ROWS]
  3280 00002403 FECE                <1> 	dec	dh
  3281                              <1> vga_g_up_2:
  3282 00002405 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS]  ; = [VGA_COLS]
  3283 0000240B 7208                <1> 	jb	short vga_g_up_3
  3284 0000240D 8A15[7C660000]      <1> 	mov	dl, [CRT_COLS]
  3285 00002413 FECA                <1> 	dec	dl
  3286                              <1> vga_g_up_3:	
  3287 00002415 3A05[82660000]      <1> 	cmp	al, [VGA_ROWS]
  3288 0000241B 7602                <1> 	jna	short vga_g_up_4
  3289 0000241D 28C0                <1> 	sub	al, al ; 0
  3290                              <1> vga_g_up_4:
  3291 0000241F 88D7                <1> 	mov	bh, dl ; clr
  3292 00002421 28CF                <1> 	sub	bh, cl ; cul
  3293 00002423 FEC7                <1> 	inc	bh ; cols = clr-cul+1
  3294                              <1> 
  3295 00002425 20C0                <1> 	and	al, al ; nblines = 0
  3296 00002427 755D                <1> 	jnz	short vga_g_up_6
  3297 00002429 20ED                <1> 	and	ch, ch ; rul = 0
  3298 0000242B 7559                <1> 	jnz	short vga_g_up_6
  3299 0000242D 20C9                <1> 	and	cl, cl ; cul = 0
  3300 0000242F 7555                <1> 	jnz	short vga_g_up_6
  3301                              <1> 
  3302 00002431 6650                <1> 	push	ax
  3303 00002433 A0[82660000]        <1> 	mov	al, [VGA_ROWS]
  3304 00002438 FEC8                <1> 	dec	al  
  3305 0000243A 38C6                <1> 	cmp	dh, al ; rlr = nbrows-1
  3306 0000243C 7546                <1> 	jne	short vga_g_up_5
  3307 0000243E A0[7C660000]        <1>         mov     al, [CRT_COLS]  ; = VGA_COLS
  3308 00002443 FEC8                <1> 	dec	al 
  3309 00002445 38C2                <1>  	cmp	dl, al ; clr = nbcols-1
  3310 00002447 753B                <1> 	jne	short vga_g_up_5
  3311 00002449 6658                <1> 	pop	ax
  3312                              <1> 
  3313 0000244B 66B80502            <1> 	mov	ax, 0205h
  3314 0000244F 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3315 00002453 66EF                <1> 	out	dx, ax
  3316 00002455 A0[82660000]        <1> 	mov	al, [VGA_ROWS]
  3317 0000245A 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; = [VGA_COLS]
  3318 00002460 F6E4                <1> 	mul	ah
  3319 00002462 0FB7D0              <1> 	movzx	edx, ax
  3320                              <1> 	; 08/08/2016
  3321 00002465 0FB605[7E660000]    <1> 	movzx	eax, byte [CHAR_HEIGHT]
  3322 0000246C F7E2                <1> 	mul	edx
  3323                              <1> 	; eax = byte count	
  3324 0000246E 89C1                <1> 	mov	ecx, eax
  3325                              <1> 	;; 07/08/2016
  3326                              <1> 	;shl	dx, 3 ; * 8 ; * [CHAR_HEIGHT]
  3327                              <1> 	;mov	ecx, edx
  3328 00002470 88D8                <1> 	mov	al, bl ; fill value for blanked lines
  3329 00002472 BF00000A00          <1> 	mov	edi, 0A0000h
  3330 00002477 F3AA                <1> 	rep	stosb		
  3331                              <1> 	
  3332 00002479 66B80500            <1> 	mov	ax, 5
  3333 0000247D 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3334 00002481 66EF                <1> 	out	dx, ax ; 0005h	
  3335                              <1> 
  3336 00002483 C3                  <1> 	retn
  3337                              <1> 
  3338                              <1> vga_g_up_5:
  3339 00002484 6658                <1> 	pop	ax
  3340                              <1> 
  3341                              <1> vga_g_up_6:
  3342                              <1> 	; [ESI] = VGA memory model number for current video mode
  3343                              <1>         ;
  3344                              <1>         ; LINEAR8 equ 5
  3345                              <1>         ; PLANAR4 equ 4
  3346                              <1>         ; PLANAR1 equ 3
  3347                              <1> 
  3348 00002486 803E04              <1> 	cmp	byte [esi], PLANAR4
  3349 00002489 7424                <1> 	je	short vga_g_up_planar
  3350 0000248B 803E03              <1> 	cmp	byte [esi], PLANAR1
  3351 0000248E 741F                <1> 	je	short vga_g_up_planar
  3352                              <1> vga_g_up_linear8:
  3353                              <1> 	; 07/07/2016 (TEMPORARY)
  3354                              <1> 	;
  3355                              <1> 	; cl = upper left column ; cul
  3356                              <1> 	; ch = upper left row ; rul
  3357                              <1> 	; dl = lower rigth column ; clr
  3358                              <1> 	; dh = lower right row ; rlr
  3359                              <1> 
  3360                              <1> vga_g_up_l0:
  3361                              <1>  	;{for(i=rul;i<=rlr;i++)
  3362                              <1>   	; if((i+nblines>rlr)||(nblines==0))
  3363 00002490 08C0                <1> 	or	al, al
  3364 00002492 7414                <1> 	jz	short vga_g_up_l2
  3365 00002494 88C4                <1> 	mov	ah, al
  3366 00002496 00EC                <1> 	add	ah, ch ; i+nblines
  3367                              <1> 	;jc	short vga_g_up_l2	
  3368 00002498 38F4                <1> 	cmp	ah, dh
  3369 0000249A 770C                <1> 	ja	short vga_g_up_l2
  3370                              <1> 	; else
  3371                              <1> 	;  vgamem_copy_pl4(cul,i+nblines,i,cols,nbcols,cheight);
  3372 0000249C E8F2000000          <1> 	call	vgamem_copy_l8
  3373                              <1> vga_g_up_l1:
  3374 000024A1 FEC5                <1> 	inc	ch
  3375 000024A3 38F5                <1> 	cmp	ch, dh
  3376 000024A5 76E9                <1> 	jna	short vga_g_up_l0
  3377 000024A7 C3                  <1> 	retn
  3378                              <1> vga_g_up_l2:
  3379                              <1> 	; vgamem_fill_pl4(cul,i,cols,nbcols,cheight,attr);
  3380 000024A8 E850010000          <1> 	call	vgamem_fill_l8
  3381 000024AD EBF2                <1> 	jmp	short vga_g_up_l1
  3382                              <1> 
  3383                              <1> vga_g_up_planar:
  3384                              <1> 	; cl = upper left column ; cul
  3385                              <1> 	; ch = upper left row ; rul
  3386                              <1> 	; dl = lower rigth column ; clr
  3387                              <1> 	; dh = lower right row ; rlr
  3388                              <1> vga_g_up_pl0:
  3389                              <1>  	;{for(i=rul;i<=rlr;i++)
  3390                              <1>   	; if((i+nblines>rlr)||(nblines==0))
  3391 000024AF 20C0                <1> 	and	al, al
  3392 000024B1 7414                <1> 	jz	short vga_g_up_pl2	
  3393 000024B3 88C4                <1> 	mov	ah, al
  3394 000024B5 00EC                <1> 	add	ah, ch ; i+nblines
  3395                              <1> 	;jc	short vga_g_up_pl2
  3396 000024B7 38F4                <1> 	cmp	ah, dh
  3397 000024B9 770C                <1> 	ja	short vga_g_up_pl2
  3398                              <1> 	; else
  3399                              <1> 	;  vgamem_copy_pl4(cul,i+nblines,i,cols,nbcols,cheight);
  3400 000024BB E80E000000          <1> 	call	vgamem_copy_pl4
  3401                              <1> vga_g_up_pl1:
  3402 000024C0 FEC5                <1> 	inc	ch 
  3403 000024C2 38F5                <1> 	cmp	ch, dh
  3404 000024C4 76E9                <1> 	jna	short vga_g_up_pl0
  3405 000024C6 C3                  <1> 	retn
  3406                              <1> vga_g_up_pl2:
  3407                              <1> 	; vgamem_fill_pl4(cul,i,cols,nbcols,cheight,attr);
  3408 000024C7 E870000000          <1> 	call	vgamem_fill_pl4
  3409 000024CC EBF2                <1> 	jmp	short vga_g_up_pl1
  3410                              <1> 
  3411                              <1> vgamem_copy_pl4:
  3412                              <1> 	; 08/08/2016
  3413                              <1> 	; 07/08/2016
  3414                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3415                              <1> 	;
  3416                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3417                              <1> 	; vgabios-0.7a (2011)
  3418                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3419                              <1> 	; 'vgabios.c', 'vgamem_copy_pl4'
  3420                              <1> 	;
  3421                              <1> 	; vgamem_copy_pl4(xstart,ysrc,ydest,cols,nbcols,cheight)
  3422                              <1> 	; cl = xstart, ah = ysrc (i+nblines), ch = ydest (i),
  3423                              <1> 	; bh = cols, [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight
  3424                              <1> 
  3425                              <1> 	; src=ysrc*cheight*nbcols+xstart;
  3426                              <1> 	; dest=ydest*cheight*nbcols+xstart;
  3427                              <1> 
  3428 000024CE 52                  <1> 	push	edx
  3429 000024CF 50                  <1> 	push	eax
  3430                              <1> 
  3431                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0105)
  3432 000024D0 66B80501            <1> 	mov	ax, 0105h
  3433 000024D4 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3434 000024D8 66EF                <1> 	out	dx, ax
  3435                              <1> 
  3436                              <1> 	; 07/08/2016
  3437                              <1>  	;mov     ah, [esp+1]
  3438                              <1> 	;movzx	edx, ah ; ysrc
  3439 000024DA 0FB6542401          <1> 	movzx	edx, byte [esp+1]
  3440                              <1> 	; 08/08/2016
  3441 000024DF 0FB605[7E660000]    <1> 	movzx	eax, byte [CHAR_HEIGHT]
  3442 000024E6 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; nbcols
  3443 000024EC F6E4                <1> 	mul	ah 
  3444                              <1> 	;; 07/08/2016
  3445                              <1> 	;movzx	eax, byte [CRT_COLS]
  3446                              <1> 	;shl	ax, 3 ; * 8 ; * [CHAR_HEIGHT]
  3447 000024EE 50                  <1> 	push	eax ; cheight * nbcols
  3448 000024EF F7E2                <1> 	mul	edx ; * ysrc
  3449                              <1> 	; eax = ysrc * cheight * nbcols
  3450                              <1> 	; edx = 0
  3451 000024F1 88CA                <1> 	mov	dl, cl ; edx = xstart	
  3452 000024F3 01D0                <1>  	add	eax, edx
  3453 000024F5 89C6                <1> 	mov	esi, eax ; src
  3454 000024F7 88EA                <1> 	mov	dl, ch ; ydest
  3455 000024F9 58                  <1> 	pop	eax ; cheight * nbcols
  3456 000024FA F7E2                <1> 	mul	edx
  3457                              <1> 	; eax = ydest * cheight * nbcols
  3458 000024FC 88CA                <1> 	mov	dl, cl ; edx = xstart	
  3459 000024FE 01D0                <1>  	add	eax, edx
  3460 00002500 89C7                <1> 	mov	edi, eax ; dest
  3461                              <1> 	; esi = src
  3462                              <1> 	; edi = dest
  3463                              <1> 	; for(i=0;i<cheight;i++)
  3464                              <1>   	; {
  3465                              <1>    	;  memcpyb(0xa000,dest+i*nbcols,0xa000,src+i*nbcols,cols);
  3466                              <1>   	; }
  3467 00002502 51                  <1> 	push	ecx
  3468 00002503 B900000A00          <1> 	mov	ecx, 0A0000h
  3469 00002508 01CE                <1> 	add	esi, ecx
  3470 0000250A 01CF                <1> 	add	edi, ecx
  3471                              <1> 	; 08/08/2016
  3472 0000250C 8A35[7E660000]      <1> 	mov	dh, [CHAR_HEIGHT]
  3473                              <1> 	;; 07/08/2016
  3474                              <1> 	;mov	dh, 8 ; 07/08/2016
  3475 00002512 28D2                <1> 	sub	dl, dl ; i
  3476                              <1> vgamem_copy_pl4_0:
  3477 00002514 56                  <1> 	push	esi
  3478 00002515 57                  <1> 	push	edi
  3479 00002516 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS]
  3480 0000251D F6E2                <1> 	mul	dl
  3481                              <1> 	; eax = i * nbcols
  3482 0000251F 01C7                <1> 	add	edi, eax ; dest+i*nbcols
  3483 00002521 01C6                <1> 	add	esi, eax
  3484 00002523 0FB6CF              <1> 	movzx	ecx, bh ; cols
  3485 00002526 F3A4                <1> 	rep	movsb
  3486 00002528 5F                  <1> 	pop	edi
  3487 00002529 5E                  <1> 	pop	esi
  3488 0000252A FECE                <1> 	dec	dh
  3489 0000252C 75E6                <1> 	jnz	short vgamem_copy_pl4_0
  3490                              <1> vgamem_copy_pl4_1:
  3491 0000252E 59                  <1> 	pop	ecx
  3492                              <1> 
  3493                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0005);
  3494 0000252F 66B80500            <1> 	mov	ax, 0005h
  3495 00002533 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3496 00002537 66EF                <1> 	out	dx, ax
  3497                              <1> 
  3498 00002539 58                  <1> 	pop	eax
  3499 0000253A 5A                  <1> 	pop	edx
  3500                              <1> 
  3501 0000253B C3                  <1> 	retn	
  3502                              <1> 
  3503                              <1> vgamem_fill_pl4:
  3504                              <1> 	; 08/08/2016
  3505                              <1> 	; 07/08/2016
  3506                              <1> 	; 04/08/2016
  3507                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3508                              <1> 	;
  3509                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3510                              <1> 	; vgabios-0.7a (2011)
  3511                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3512                              <1> 	; 'vgabios.c', 'vgamem_fill_pl4'
  3513                              <1> 	;
  3514                              <1> 	; vgamem_fill_pl4(xstart,ystart,cols,nbcols,cheight,attr)
  3515                              <1> 	; cl = xstart, edi = ch = ystart, bh = cols,
  3516                              <1> 	; [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight, attr = 0
  3517                              <1> 
  3518                              <1> 	; dest=ystart*cheight*nbcols+xstart;
  3519 0000253C 52                  <1> 	push	edx
  3520 0000253D 50                  <1> 	push	eax
  3521                              <1> 
  3522                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0205)
  3523 0000253E 66B80502            <1> 	mov	ax, 0205h
  3524 00002542 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3525 00002546 66EF                <1> 	out	dx, ax
  3526                              <1> 
  3527                              <1>       	; 08/08/2016
  3528 00002548 0FB605[7E660000]    <1> 	movzx   eax, byte [CHAR_HEIGHT]
  3529 0000254F F6E5                <1> 	mul	ch
  3530                              <1> 	;; 07/08/2016
  3531                              <1> 	;movzx	eax, ch
  3532                              <1> 	;shl	ax, 3 ; * 8 ; * [CHAR_HEIGHT]
  3533 00002551 0FB615[7C660000]    <1> 	movzx	edx, byte [CRT_COLS] ; = [VGA_COLS]
  3534 00002558 F7E2                <1> 	mul	edx
  3535                              <1> 	; edx  = 0
  3536 0000255A 88CA                <1> 	mov	dl, cl 
  3537 0000255C 01D0                <1> 	add	eax, edx
  3538 0000255E 89C7                <1> 	mov	edi, eax
  3539                              <1> 	; edi = dest
  3540                              <1> 	; for(i=0;i<cheight;i++)
  3541                              <1>   	; {
  3542                              <1>    	;  memsetb(0xa000,dest+i*nbcols,attr,cols);
  3543                              <1>   	; }
  3544 00002560 81C700000A00        <1> 	add	edi, 0A0000h
  3545 00002566 51                  <1> 	push	ecx
  3546                              <1> 	; 08/08/2016
  3547 00002567 8A35[7E660000]      <1> 	mov	dh, [CHAR_HEIGHT]
  3548                              <1> 	;; 07/08/2016
  3549                              <1> 	;mov	dh, 8 ; 07/08/2016
  3550 0000256D 28D2                <1> 	sub	dl, dl ; i
  3551                              <1> vgamem_fill_pl4_0:
  3552 0000256F 57                  <1> 	push	edi
  3553 00002570 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS]
  3554 00002577 F6E2                <1> 	mul	dl
  3555                              <1> 	; eax = i * nbcols
  3556 00002579 01C7                <1> 	add	edi, eax ; dest+i*nbcols
  3557 0000257B 88D8                <1> 	mov	al, bl ; attr ; 04/08/2016
  3558 0000257D 0FB6CF              <1> 	movzx	ecx, bh ; cols
  3559 00002580 F3AA                <1>  	rep	stosb
  3560 00002582 5F                  <1> 	pop	edi
  3561 00002583 75EA                <1> 	jnz	short vgamem_fill_pl4_0
  3562                              <1> vgamem_fill_pl4_1:
  3563 00002585 59                  <1> 	pop	ecx
  3564                              <1> 
  3565                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0005);
  3566 00002586 66B80500            <1> 	mov	ax, 0005h
  3567 0000258A 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3568 0000258E 66EF                <1> 	out	dx, ax
  3569                              <1> 
  3570 00002590 58                  <1> 	pop	eax
  3571 00002591 5A                  <1> 	pop	edx 
  3572                              <1> 	
  3573 00002592 C3                  <1> 	retn
  3574                              <1> 
  3575                              <1> vgamem_copy_l8:
  3576                              <1> 	; 08/08/2016
  3577                              <1> 	; 07/08/2016
  3578                              <1> 	; 06/08/2016
  3579                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3580                              <1> 	;
  3581                              <1> 	; TEMPORARY
  3582                              <1> 	;
  3583                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3584                              <1> 	; vgabios-0.7a (2011)
  3585                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3586                              <1> 	; 'vgabios.c', 'vgamem_copy_pl4'
  3587                              <1> 	;
  3588                              <1> 	; vgamem_copy_pl4(xstart,ysrc,ydest,cols,nbcols,cheight)
  3589                              <1> 	; cl = xstart, ah = ysrc (i+nblines), ch = ydest (i),
  3590                              <1> 	; bh = cols, [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight
  3591                              <1> 
  3592                              <1> 	; src=ysrc*cheight*nbcols+xstart;
  3593                              <1> 	; dest=ydest*cheight*nbcols+xstart;
  3594                              <1> 
  3595 00002593 52                  <1> 	push	edx
  3596 00002594 50                  <1> 	push	eax
  3597                              <1> 
  3598                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0105)
  3599                              <1> 	;mov	ax, 0105h
  3600                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3601                              <1> 	;out	dx, ax
  3602                              <1> 
  3603                              <1> 	;mov	ah, [esp+1]
  3604                              <1> 
  3605 00002595 0FB6D4              <1> 	movzx	edx, ah ; ysrc
  3606                              <1> 	; 08/08/2016
  3607 00002598 0FB605[7E660000]    <1> 	movzx	eax, byte [CHAR_HEIGHT]
  3608 0000259F 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; nbcols
  3609 000025A5 F6E4                <1> 	mul	ah 
  3610                              <1> 	;; 07/08/2016
  3611                              <1> 	;movzx	eax, byte [CRT_COLS]
  3612                              <1> 	;shl	ax, 3 ; * 8 ; * [CHAR_HEIGHT]
  3613 000025A7 50                  <1> 	push	eax ; cheight * nbcols
  3614 000025A8 F7E2                <1> 	mul	edx ; * ysrc
  3615                              <1> 	; eax = ysrc * cheight * nbcols
  3616                              <1> 	; edx = 0
  3617 000025AA 88CA                <1> 	mov	dl, cl ; edx = xstart
  3618 000025AC 01D0                <1>  	add	eax, edx
  3619 000025AE 89C6                <1> 	mov	esi, eax ; src
  3620 000025B0 66C1E603            <1> 	shl	si, 3 ; * 8 ; 06/08/2016
  3621 000025B4 88EA                <1> 	mov	dl, ch ; ydest
  3622 000025B6 58                  <1> 	pop	eax ; cheight * nbcols
  3623 000025B7 F7E2                <1> 	mul	edx
  3624                              <1> 	; eax = ydest * cheight * nbcols
  3625 000025B9 88CA                <1> 	mov	dl, cl ; edx = xstart	
  3626 000025BB 01D0                <1>  	add	eax, edx
  3627 000025BD 89C7                <1> 	mov	edi, eax ; dest
  3628 000025BF 66C1E703            <1> 	shl	di, 3 ; * 8 ; 06/08/2016
  3629                              <1> 	; esi = src
  3630                              <1> 	; edi = dest
  3631                              <1> 	; for(i=0;i<cheight;i++)
  3632                              <1>   	; {
  3633                              <1>    	;  memcpyb(0xa000,dest+i*nbcols,0xa000,src+i*nbcols,cols);
  3634                              <1>   	; }
  3635 000025C3 51                  <1> 	push	ecx
  3636 000025C4 B900000A00          <1> 	mov	ecx, 0A0000h
  3637 000025C9 01CE                <1> 	add	esi, ecx
  3638 000025CB 01CF                <1> 	add	edi, ecx
  3639                              <1> 	; 08/08/2016
  3640 000025CD 8A35[7E660000]      <1> 	mov	dh, [CHAR_HEIGHT]
  3641                              <1> 	;; 07/08/2016
  3642                              <1> 	;mov	dh, 8 ; 07/08/2016
  3643 000025D3 28D2                <1> 	sub	dl, dl ; i
  3644                              <1> vgamem_copy_l8_0:
  3645 000025D5 56                  <1> 	push	esi
  3646 000025D6 57                  <1> 	push	edi
  3647 000025D7 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS]
  3648 000025DE F6E2                <1> 	mul	dl
  3649                              <1> 	; eax = i * nbcols
  3650 000025E0 66C1E003            <1> 	shl	ax, 3 ; * 8 ; 06/08/2016
  3651 000025E4 01C7                <1> 	add	edi, eax ; dest+i*nbcols
  3652 000025E6 01C6                <1> 	add	esi, eax
  3653 000025E8 0FB6CF              <1> 	movzx	ecx, bh ; cols
  3654 000025EB 66C1E103            <1> 	shl	cx, 3 ; * 8 ; 06/08/2016
  3655 000025EF F3A4                <1> 	rep	movsb
  3656 000025F1 5F                  <1> 	pop	edi
  3657 000025F2 5E                  <1> 	pop	esi
  3658 000025F3 FEC2                <1> 	inc	dl ; 06/08/2016
  3659 000025F5 FECE                <1> 	dec	dh
  3660 000025F7 75DC                <1> 	jnz	short vgamem_copy_l8_0
  3661                              <1> vgamem_copy_l8_1:
  3662 000025F9 59                  <1> 	pop	ecx
  3663                              <1> 
  3664                              <1> 	;; outw(VGAREG_GRDC_ADDRESS, 0x0005);
  3665                              <1> 	;mov	ax, 0005h
  3666                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3667                              <1> 	;out	dx, ax
  3668                              <1> 
  3669 000025FA 58                  <1> 	pop	eax
  3670 000025FB 5A                  <1> 	pop	edx
  3671                              <1> 
  3672 000025FC C3                  <1> 	retn
  3673                              <1> 
  3674                              <1> vgamem_fill_l8:
  3675                              <1> 	; 08/08/2016
  3676                              <1> 	; 07/08/2016
  3677                              <1> 	; 06/08/2016
  3678                              <1> 	; 04/08/2016
  3679                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3680                              <1> 	;
  3681                              <1> 	; TEMPORARY
  3682                              <1> 	;
  3683                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3684                              <1> 	; vgabios-0.7a (2011)
  3685                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3686                              <1> 	; 'vgabios.c', 'vgamem_fill_pl4'
  3687                              <1> 	;
  3688                              <1> 	; vgamem_fill_pl4(xstart,ystart,cols,nbcols,cheight,attr)
  3689                              <1> 	; cl = xstart, edi = ch = ystart, bh = cols,
  3690                              <1> 	; [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight, attr = 0
  3691                              <1> 
  3692                              <1> 	; dest=ystart*cheight*nbcols+xstart;
  3693 000025FD 52                  <1> 	push	edx
  3694 000025FE 50                  <1> 	push	eax
  3695                              <1> 
  3696                              <1> 	;; outw(VGAREG_GRDC_ADDRESS, 0x0205)
  3697                              <1> 	;mov	ax, 0205h
  3698                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3699                              <1> 	;out	dx, ax
  3700                              <1> 
  3701                              <1>         ; 08/08/2016
  3702 000025FF 0FB605[7E660000]    <1> 	movzx   eax, byte [CHAR_HEIGHT]
  3703 00002606 F6E5                <1> 	mul	ch
  3704                              <1> 	;; 07/08/2016
  3705                              <1> 	;movzx	eax, ch
  3706                              <1> 	;shl	ax, 3 ; * 8 ; * [CHAR_HEIGHT]
  3707 00002608 0FB615[7C660000]    <1> 	movzx	edx, byte [CRT_COLS] ; = [VGA_COLS]
  3708 0000260F F7E2                <1> 	mul	edx
  3709                              <1> 	; edx  = 0
  3710 00002611 88CA                <1> 	mov	dl, cl 
  3711 00002613 01D0                <1> 	add	eax, edx
  3712 00002615 89C7                <1> 	mov	edi, eax
  3713 00002617 66C1E703            <1> 	shl	di, 3 ; * 8 ; 06/08/2016
  3714                              <1> 	; edi = dest
  3715                              <1> 	; for(i=0;i<cheight;i++)
  3716                              <1>   	; {
  3717                              <1>    	;  memsetb(0xa000,dest+i*nbcols,attr,cols);
  3718                              <1>   	; }
  3719 0000261B 81C700000A00        <1> 	add	edi, 0A0000h
  3720 00002621 51                  <1> 	push	ecx
  3721                              <1> 	; 08/08/2016
  3722 00002622 8A35[7E660000]      <1> 	mov	dh, [CHAR_HEIGHT]
  3723                              <1> 	;; 07/08/2016
  3724                              <1> 	;mov	dh, 8 ; 07/08/2016
  3725 00002628 28D2                <1> 	sub	dl, dl ; i
  3726                              <1> vgamem_fill_l8_0:
  3727 0000262A 57                  <1> 	push	edi
  3728 0000262B 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS]
  3729 00002632 F6E2                <1> 	mul	dl
  3730                              <1> 	; eax = i * nbcols
  3731 00002634 66C1E003            <1> 	shl	ax, 3 ; * 8 ; 06/08/2016
  3732 00002638 01C7                <1> 	add	edi, eax ; dest+i*nbcols
  3733 0000263A 88D8                <1> 	mov	al, bl ; attr ; 04/08/2016
  3734 0000263C 0FB6CF              <1> 	movzx	ecx, bh ; cols
  3735 0000263F 66C1E103            <1> 	shl	cx, 3 ; * 8 ; 06/08/2016
  3736 00002643 F3AA                <1>  	rep	stosb
  3737 00002645 5F                  <1> 	pop	edi
  3738 00002646 FEC2                <1> 	inc	dl ; 06/08/2016
  3739 00002648 FECE                <1> 	dec	dh
  3740 0000264A 75DE                <1> 	jnz	short vgamem_fill_l8_0
  3741                              <1> vgamem_fill_l8_1:
  3742 0000264C 59                  <1> 	pop	ecx
  3743                              <1> 
  3744                              <1> 	;; outw(VGAREG_GRDC_ADDRESS, 0x0005);
  3745                              <1> 	;mov	ax, 0005h
  3746                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3747                              <1> 	;out	dx, ax
  3748                              <1> 
  3749 0000264D 58                  <1> 	pop	eax
  3750 0000264E 5A                  <1> 	pop	edx 
  3751                              <1> 
  3752 0000264F C3                  <1> 	retn
  3753                              <1> 
  3754                              <1> vga_graphics_down:
  3755                              <1> 	; 08/08/2016
  3756                              <1> 	; 07/08/2016
  3757                              <1> 	; 31/07/2016
  3758                              <1> 	; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
  3759                              <1> 	;
  3760                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  3761                              <1> 	; vgabios-0.7a (2011)
  3762                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  3763                              <1> 	; 'vgabios.c', 'biosfn_scroll'
  3764                              <1> 	;
  3765                              <1> 
  3766                              <1> 	; cl = upper left column
  3767                              <1> 	; ch = upper left row
  3768                              <1> 	; dl = lower rigth column
  3769                              <1> 	; dh = lower right row
  3770                              <1> 	;
  3771                              <1> 	; al = line count (AL=0 means blank entire fields)
  3772                              <1> 	; bl = fill value for blanked lines	
  3773                              <1> 	; bh = unused
  3774                              <1> 	;
  3775                              <1> 	; ah = [CRT_MODE], current video mode	
  3776                              <1> 
  3777 00002650 FC                  <1>         cld     ; !!! Clear direction flag !!! 
  3778                              <1> 
  3779 00002651 88C7                <1> 	mov	bh, al ; 31/07/2016
  3780                              <1> 
  3781 00002653 BE[96660000]        <1> 	mov	esi, vga_modes
  3782 00002658 89F7                <1> 	mov	edi, esi
  3783 0000265A 83C710              <1> 	add	edi, vga_mode_count
  3784                              <1> vga_g_down_0:
  3785 0000265D AC                  <1> 	lodsb
  3786 0000265E 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  3787 00002660 7405                <1> 	je	short vga_g_down_1
  3788 00002662 39FE                <1> 	cmp	esi, edi
  3789 00002664 72F7                <1> 	jb	short vga_g_down_0
  3790                              <1> 	; xor 	bh, bh	; 31/07/2016
  3791 00002666 C3                  <1> 	retn	; nothing to do
  3792                              <1> vga_g_down_1:
  3793 00002667 88F8                <1> 	mov	al, bh ; 31/07/2016
  3794 00002669 83C64F              <1> 	add	esi, vga_memmodel - (vga_modes + 1)  
  3795                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  3796                              <1> 	
  3797                              <1> 	; if(rlr>=nbrows)rlr=nbrows-1;
  3798                              <1>  	; if(clr>=nbcols)clr=nbcols-1;
  3799                              <1>  	; if(nblines>nbrows)nblines=0;
  3800                              <1>  	; cols=clr-cul+1;
  3801                              <1> 
  3802 0000266C 3A35[82660000]      <1> 	cmp	dh, [VGA_ROWS]
  3803 00002672 7208                <1> 	jb	short vga_g_down_2
  3804 00002674 8A35[82660000]      <1> 	mov	dh, [VGA_ROWS]
  3805 0000267A FECE                <1> 	dec	dh
  3806                              <1> vga_g_down_2:
  3807 0000267C 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS]  ; = [VGA_COLS]
  3808 00002682 7208                <1> 	jb	short vga_g_down_3
  3809 00002684 8A15[7C660000]      <1> 	mov	dl, [CRT_COLS]
  3810 0000268A FECA                <1> 	dec	dl
  3811                              <1> vga_g_down_3:	
  3812 0000268C 3A05[82660000]      <1> 	cmp	al, [VGA_ROWS]
  3813 00002692 7602                <1> 	jna	short vga_g_down_4
  3814 00002694 28C0                <1> 	sub	al, al ; 0
  3815                              <1> vga_g_down_4:
  3816 00002696 88F7                <1> 	mov	bh, dh ; clr
  3817 00002698 28CF                <1> 	sub	bh, cl ; cul
  3818 0000269A FEC7                <1> 	inc	bh ; cols = clr-cul+1
  3819                              <1> 
  3820 0000269C 20C0                <1> 	and	al, al ; nblines = 0
  3821 0000269E 755B                <1> 	jnz	short vga_g_down_6
  3822 000026A0 20ED                <1> 	and	ch, ch ; rul = 0
  3823 000026A2 7557                <1> 	jnz	short vga_g_down_6
  3824 000026A4 20C9                <1> 	and	cl, cl ; cul = 0
  3825 000026A6 7553                <1> 	jnz	short vga_g_down_6
  3826                              <1> 
  3827 000026A8 6650                <1> 	push	ax
  3828 000026AA A0[82660000]        <1> 	mov	al, [VGA_ROWS]
  3829 000026AF FEC8                <1> 	dec	al  
  3830 000026B1 38C6                <1> 	cmp	dh, al ; rlr = nbrows-1
  3831 000026B3 7544                <1> 	jne	short vga_g_down_5
  3832 000026B5 A0[7C660000]        <1>         mov     al, [CRT_COLS]  ; = VGA_COLS
  3833 000026BA FEC8                <1> 	dec	al 
  3834 000026BC 38C2                <1>  	cmp	dl, al ; clr = nbcols-1
  3835 000026BE 7539                <1> 	jne	short vga_g_down_5
  3836 000026C0 6658                <1> 	pop	ax
  3837                              <1> 
  3838 000026C2 66B80502            <1> 	mov	ax, 0205h
  3839 000026C6 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3840 000026CA 66EF                <1> 	out	dx, ax
  3841 000026CC A0[82660000]        <1> 	mov	al, [VGA_ROWS]
  3842 000026D1 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; = [VGA_COLS]
  3843 000026D7 F6E4                <1> 	mul	ah
  3844 000026D9 0FB7D0              <1> 	movzx	edx, ax
  3845                              <1> 	; 08/08/2016
  3846 000026DC 0FB605[7E660000]    <1> 	movzx	eax, byte [CHAR_HEIGHT]
  3847 000026E3 F7E2                <1> 	mul	edx
  3848                              <1> 	; eax = byte count	
  3849 000026E5 89C1                <1> 	mov	ecx, eax
  3850                              <1> 	;; 07/08/2016
  3851                              <1> 	;shl	dx, 3 ; * 8 ; * [CHAR_HEIGHT]
  3852                              <1> 	;mov	ecx, edx
  3853 000026E7 88D8                <1> 	mov	al, bl ; fill value for blanked lines
  3854 000026E9 BF00000A00          <1> 	mov	edi, 0A0000h
  3855 000026EE F3AA                <1> 	rep	stosb			
  3856                              <1> 	
  3857 000026F0 B005                <1> 	mov	al, 5
  3858 000026F2 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  3859 000026F6 66EF                <1> 	out	dx, ax ; 0005h	
  3860                              <1> 
  3861 000026F8 C3                  <1> 	retn
  3862                              <1> 
  3863                              <1> vga_g_down_5:
  3864 000026F9 6658                <1> 	pop	ax
  3865                              <1> 
  3866                              <1> vga_g_down_6:
  3867                              <1> 	; [ESI] = VGA memory model number for current video mode
  3868                              <1>         ;
  3869                              <1>         ; LINEAR8 equ 5
  3870                              <1>         ; PLANAR4 equ 4
  3871                              <1>         ; PLANAR1 equ 3
  3872                              <1> 
  3873 000026FB 803E04              <1> 	cmp	byte [esi], PLANAR4
  3874 000026FE 742C                <1> 	je	short vga_g_down_planar
  3875 00002700 803E03              <1> 	cmp	byte [esi], PLANAR1
  3876 00002703 7427                <1> 	je	short vga_g_down_planar
  3877                              <1> vga_g_down_linear8:
  3878                              <1> 	; 07/07/2016 (TEMPORARY)
  3879                              <1> 	;
  3880                              <1> 	; cl = upper left column ; cul
  3881                              <1> 	; ch = upper left row ; rul
  3882                              <1> 	; dl = lower rigth column ; clr
  3883                              <1> 	; dh = lower right row ; rlr
  3884                              <1> 
  3885                              <1> vga_g_down_l0:
  3886                              <1> 	;{for(i=rlr;i>=rul;i--)
  3887                              <1>         ; if((i<rul+nblines)||(nblines==0))
  3888 00002705 08C0                <1> 	or	al, al
  3889 00002707 741C                <1> 	jz	short vga_g_down_l2
  3890 00002709 88C4                <1> 	mov	ah, al
  3891 0000270B 00EC                <1> 	add	ah, ch
  3892                              <1> 	;jc	short vga_g_down_l2	
  3893 0000270D 86EE                <1> 	xchg	ch, dh
  3894 0000270F 38E5                <1> 	cmp	ch, ah
  3895 00002711 7212                <1> 	jb	short vga_g_down_l2
  3896 00002713 88EC                <1> 	mov	ah, ch
  3897 00002715 28C4                <1> 	sub	ah, al ; ah = i - nblines
  3898                              <1> 	; else
  3899                              <1> 	; vgamem_copy_pl4(cul,i,i-nblines,cols,nbcols,cheight);
  3900 00002717 E877FEFFFF          <1> 	call	vgamem_copy_l8
  3901                              <1> vga_g_down_l1:
  3902 0000271C 86F5                <1> 	xchg	dh, ch
  3903 0000271E FECE                <1> 	dec	dh 
  3904 00002720 38EE                <1> 	cmp	dh, ch
  3905 00002722 73E1                <1> 	jnb	short vga_g_down_l0
  3906 00002724 C3                  <1> 	retn
  3907                              <1> 
  3908                              <1> vga_g_down_l2:
  3909                              <1> 	; vgamem_fill_pl4(cul,i,cols,nbcols,cheight,attr);
  3910 00002725 E8D3FEFFFF          <1> 	call	vgamem_fill_l8
  3911 0000272A EBF0                <1> 	jmp	short vga_g_down_l1
  3912                              <1> 		 
  3913                              <1> vga_g_down_planar:
  3914                              <1> 	; cl = upper left column ; cul
  3915                              <1> 	; ch = upper left row ; rul
  3916                              <1> 	; dl = lower rigth column ; clr
  3917                              <1> 	; dh = lower right row ; rlr
  3918                              <1> vga_g_down_pl0:
  3919                              <1>  	;{for(i=rlr;i>=rul;i--)
  3920                              <1>         ; if((i<rul+nblines)||(nblines==0))
  3921 0000272C 08C0                <1> 	or	al, al
  3922 0000272E 741C                <1> 	jz	short vga_g_down_pl2
  3923 00002730 88C4                <1> 	mov	ah, al
  3924 00002732 00EC                <1> 	add	ah, ch
  3925                              <1> 	;jc	short vga_g_down_pl2	
  3926 00002734 86EE                <1> 	xchg	ch, dh
  3927 00002736 38E5                <1> 	cmp	ch, ah
  3928 00002738 7212                <1> 	jb	short vga_g_down_pl2
  3929 0000273A 88EC                <1> 	mov	ah, ch
  3930 0000273C 28C4                <1> 	sub	ah, al ; ah = i - nblines
  3931                              <1> 	; else
  3932                              <1> 	; vgamem_copy_pl4(cul,i,i-nblines,cols,nbcols,cheight);
  3933 0000273E E88BFDFFFF          <1> 	call	vgamem_copy_pl4
  3934                              <1> vga_g_down_pl1:
  3935 00002743 86F5                <1> 	xchg	dh, ch
  3936 00002745 FECE                <1> 	dec	dh 
  3937 00002747 38EE                <1> 	cmp	dh, ch
  3938 00002749 73E1                <1> 	jnb	short vga_g_down_pl0
  3939 0000274B C3                  <1> 	retn
  3940                              <1> 
  3941                              <1> vga_g_down_pl2:
  3942                              <1> 	; vgamem_fill_pl4(cul,i,cols,nbcols,cheight,attr);
  3943 0000274C E8EBFDFFFF          <1> 	call	vgamem_fill_pl4
  3944 00002751 EBF0                <1> 	jmp	short vga_g_down_pl1
  3945                              <1> 
  3946                              <1> ; 07/07/2016
  3947                              <1> ; 27/06/2016 - TRDOS 386 (TRDOS v2.0)
  3948                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  3949                              <1> ;------------------------------------------------------
  3950                              <1> ; SCROLL DOWN
  3951                              <1> ;  THIS ROUTINE SCROLLS DOWN THE INFORMATION ON THE CRT
  3952                              <1> ; ENTRY --
  3953                              <1> ;  CH,CL = UPPER LEFT CORNER OF REGION TO SCROLL
  3954                              <1> ;  DH,DL = LOWER RIGHT CORNER OF REGION TO SCROLL
  3955                              <1> ;   BOTH OF THE ABOVE ARE IN CHARACTER POSITIONS
  3956                              <1> ;  BH = FILL VALUE FOR BLANKED LINES
  3957                              <1> ;  AL = # LINES TO SCROLL (AL=0 MEANS BLANK THE ENTIRE FIELD)
  3958                              <1> ;  DS = DATA SEGMENT
  3959                              <1> ;  ES = REGEN SEGMENT
  3960                              <1> ; EXIT --
  3961                              <1> ;  NOTHING, THE SCREEN IS SCROLLED
  3962                              <1> ;--------------------------------------------------------
  3963                              <1> 
  3964                              <1> 	; cl = upper left column
  3965                              <1> 	; ch = upper left row
  3966                              <1> 	; dl = lower rigth column
  3967                              <1> 	; dh = lower right row
  3968                              <1> 	;
  3969                              <1> 	; al = line count (AL=0 means blank entire fields)
  3970                              <1> 	; bl = fill value for blanked lines	
  3971                              <1> 	; bh = unused
  3972                              <1> 
  3973                              <1> GRAPHICS_DOWN:
  3974                              <1> 	; 07/07/2016
  3975                              <1> 	;AH = Current video mode, [CRT_MODE]
  3976                              <1> 	;STD				; SET DIRECTION
  3977 00002753 80FC07              <1> 	cmp	ah, 7
  3978 00002756 0F87F4FEFFFF        <1>         ja      vga_graphics_down
  3979                              <1> 	;je	_n0
  3980                              <1> 
  3981 0000275C 88C7                <1> 	MOV	bh, al			; save line count in BH
  3982 0000275E 6689D0              <1> 	MOV	AX, DX			; GET LOWER RIGHT POSITION INTO AX REG
  3983                              <1> 
  3984                              <1> ;-----	USE CHARACTER SUBROUTINE FOR POSITIONING
  3985                              <1> ;-----	ADDRESS RETURNED IS MULTIPLIED BY 2 FROM CORRECT VALUE
  3986                              <1> 
  3987 00002761 E8F2010000          <1> 	CALL	GRAPH_POSN
  3988 00002766 0FB7F8              <1> 	MOVzx	eDI, AX			; SAVE RESULT AS DESTINATION ADDRESS
  3989                              <1> 
  3990                              <1> ;-----	DETERMINE SIZE OF WINDOW
  3991                              <1> 
  3992 00002769 6629CA              <1> 	SUB	DX, CX
  3993 0000276C 6681C20101          <1>         ADD     DX, 101h                ; ADJUST VALUES
  3994 00002771 C0E602              <1> 	SAL	DH, 2			; MULTIPLY ROWS BY 4 AT 8 VERT DOTS/CHAR
  3995                              <1> 					; AND EVEN/ODD ROWS
  3996                              <1> 
  3997                              <1> ;-----	DETERMINE CRT MODE
  3998                              <1> 
  3999 00002774 803D[7A660000]06    <1> 	CMP	byte [CRT_MODE], 6	; TEST FOR MEDIUM RES
  4000 0000277B 7307                <1>         JNC     short _R12              ; FIND_SOURCE_DOWN
  4001                              <1> 
  4002                              <1> ;-----	MEDIUM RES DOWN
  4003 0000277D D0E2                <1> 	SAL	DL, 1			; # COLUMNS * 2, SINCE 2 BYTES/CHAR
  4004 0000277F 66D1E7              <1> 	SAL	DI, 1			; OFFSET *2 SINCE 2 BYTES/CHAR
  4005 00002782 6647                <1> 	INC	DI			; POINT TO LAST BYTE
  4006                              <1> 
  4007                              <1> ;-----	DETERMINE THE SOURCE ADDRESS IN THE BUFFER
  4008                              <1> 
  4009                              <1> _R12:                                   ; FIND_SOURCE_DOWN
  4010 00002784 81C700800B00        <1> 	add	edi, 0B8000h		
  4011 0000278A 6681C7F000          <1> 	ADD	DI, 240			; POINT TO LAST ROW OF PIXELS
  4012 0000278F C0E702              <1> 	sal	bh, 2			; multiply number of lines by 4
  4013 00002792 74(06)              <1> 	JZ	short 6			; IF ZERO, THEN BLANK ENTIRE FIELD
  4014 00002794 B050                <1> 	MOV	AL, 80			; 80 BYTES/ROW
  4015 00002796 F6E7                <1> 	mul	bh			; determine offset to source
  4016 00002798 89FE                <1> 	MOV	eSI, eDI		; SET UP SOURCE
  4017 0000279A 6629C6              <1> 	SUB	SI, AX			; SUBTRACT THE OFFSET
  4018 0000279D 88F4                <1> 	MOV	AH, DH			; NUMBER OF ROWS IN FIELD
  4019 0000279F 28FC                <1> 	sub	ah, bh			; determine number to move
  4020                              <1> 
  4021                              <1> ;-----	LOOP THROUGH, MOVING ONE ROW AT A TIME, BOTH EVEN AND ODD FIELDS
  4022                              <1> 
  4023                              <1> _R13:                                   ; ROW_LOOP_DOWN
  4024 000027A1 E824000000          <1>         CALL    _R17                    ; MOVE ONE ROW
  4025 000027A6 6681EE5020          <1> 	SUB	SI, 2000h+80		; MOVE TO NEXT ROW
  4026 000027AB 6681EF5020          <1> 	SUB	DI, 2000h+80
  4027 000027B0 FECC                <1> 	DEC	AH			; NUMBER OF ROWS TO MOVE
  4028 000027B2 75ED                <1>         JNZ     short _R13              ; CONTINUE TILL ALL MOVED
  4029                              <1> 
  4030                              <1> ;-----	FILL IN THE VACATED LINE(S)
  4031                              <1> _R14:                                   ; CLEAR_ENTRY_DOWN
  4032 000027B4 88D8                <1> 	mov	al, bl			; attribute to fill with
  4033                              <1> _R15_:                                  ; CLEAR_LOOP_DOWN
  4034 000027B6 E82B000000          <1> 	CALL	_R18			; CLEAR A ROW
  4035 000027BB 6681EF5020          <1> 	SUB	DI, 2000h+80		; POINT TO NEXT LINE
  4036 000027C0 FECF                <1> 	dec	bh			; number of lines to fill
  4037 000027C2 75F2                <1>         JNZ     short _R15_             ; CLEAR_LOOP_DOWN
  4038                              <1> 	; 18/11/2020
  4039 000027C4 FC                  <1> 	CLD				; RESET THE DIRECTION FLAG
  4040                              <1> 	
  4041 000027C5 C3                  <1> 	retn				; EVERYTHING DONE
  4042                              <1> 
  4043                              <1> _R16:                                   ; BLANK_FIELD_DOWN
  4044 000027C6 88F7                <1> 	mov	bh, dh			; set blank count to everything in field
  4045 000027C8 EBEA                <1>         JMP     short _R14              ; CLEAR THE FIELD
  4046                              <1> 
  4047                              <1> ; 27/06/2016 - TRDOS 386 (TRDOS v2.0)
  4048                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4049                              <1> 
  4050                              <1> ;-----	ROUTINE TO MOVE ONE ROW OF INFORMATION
  4051                              <1> 
  4052                              <1> _R17:
  4053 000027CA 0FB6CA              <1> 	MOVzx	ecx, DL			; NUMBER OF BYTES IN THE ROW
  4054 000027CD 56                  <1> 	PUSH	eSI
  4055 000027CE 57                  <1> 	PUSH	eDI			; SAVE POINTERS
  4056 000027CF F3A4                <1> 	REP	MOVSB			; MOVE THE EVEN FIELD
  4057 000027D1 5F                  <1> 	POP	eDI
  4058 000027D2 5E                  <1> 	POP	eSI
  4059 000027D3 6681C60020          <1> 	ADD	SI, 2000h
  4060 000027D8 6681C70020          <1> 	ADD	DI, 2000h		; POINT TO THE ODD FIELD
  4061 000027DD 56                  <1> 	PUSH	eSI
  4062 000027DE 57                  <1> 	PUSH	eDI			; SAVE THE POINTERS
  4063 000027DF 88D1                <1> 	MOV	CL, DL			; COUNT BACK
  4064 000027E1 F3A4                <1> 	REP	MOVSB			; MOVE THE ODD FIELD
  4065 000027E3 5F                  <1> 	POP	eDI
  4066 000027E4 5E                  <1> 	POP	eSI			; POINTERS BACK
  4067 000027E5 C3                  <1> 	RETn				; RETURN TO CALLER
  4068                              <1> 
  4069                              <1> ;-----	CLEAR A SINGLE ROW
  4070                              <1> 
  4071                              <1> _R18:
  4072 000027E6 0FB6CA              <1> 	MOVzx	ecx, DL			; NUMBER OF BYTES IN FIELD
  4073 000027E9 57                  <1> 	PUSH	eDI			; SAVE POINTER
  4074 000027EA F3AA                <1> 	REP	STOSB			; STORE THE NEW VALUE
  4075 000027EC 5F                  <1> 	POP	eDI			; POINTER BACK
  4076 000027ED 6681C70020          <1> 	ADD	DI, 2000h		; POINT TO ODD FIELD
  4077 000027F2 57                  <1> 	PUSH	eDI
  4078 000027F3 88D1                <1> 	MOV	CL, DL
  4079 000027F5 F3AA                <1> 	REP	STOSB			; FILL THE ODD FIELD
  4080 000027F7 5F                  <1> 	POP	eDI
  4081 000027F8 C3                  <1> 	RETn				; RETURN TO CALLER
  4082                              <1> 
  4083                              <1> ; 04/07/2016
  4084                              <1> ; 01/07/2016
  4085                              <1> ; 30/06/2016 - TRDOS 386 (TRDOS v2.0)
  4086                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4087                              <1> ;--------------------------------------------------
  4088                              <1> ; GRAPHICS WRITE
  4089                              <1> ;  THIS ROUTINE WRITES THE ASCII CHARACTER TO THE CURRENT
  4090                              <1> ;  POSITION ON THE SCREEN.
  4091                              <1> ; ENTRY --
  4092                              <1> ;  AL = CHARACTER TO WRITE
  4093                              <1> ;  BL = COLOR ATTRIBUTE TO BE USED FOR FOREGROUND COLOR
  4094                              <1> ;	IF BIT 7 IS SET, THE CHAR IS XOR'D INTO THE REGEN BUFFER
  4095                              <1> ;	(0 IS USED FOR THE BACKGROUND COLOR)
  4096                              <1> ;  CX = NUMBER OF CHARS TO WRITE
  4097                              <1> ;  DS = DATA SEGMENT
  4098                              <1> ;  ES = REGEN SEGMENT
  4099                              <1> ; EXIT --
  4100                              <1> ;  NOTHING IS RETURNED
  4101                              <1> ;
  4102                              <1> ; GRAPHICS READ
  4103                              <1> ;  THIS ROUTINE READS THE ASCII CHARACTER AT THE CURRENT CURSOR
  4104                              <1> ;  POSITION ON THE SCREEN BY MATCHING THE DOTS ON THE SCREEN TO THE
  4105                              <1> ;  CHARACTER GENERATOR CODE POINTS
  4106                              <1> ; ENTRY --
  4107                              <1> ;  NONE (0 IS ASSUMED AS THE BACKGROUND COLOR)
  4108                              <1> ; EXIT --
  4109                              <1> ;  AL = CHARACTER READ AT THAT POSITION (0 RETURNED IF NONE FOUND)
  4110                              <1> ;
  4111                              <1> ; FOR BOTH ROUTINES, THE IMAGES USED TO FORM CHARS ARE CONTAINED IN ROM
  4112                              <1> ;  FOR THE 1ST 128 CHARS.  TO ACCESS CHARS IN THE SECOND HALF, THE USER
  4113                              <1> ;  MUST INITIALIZE THE VECTOR AT INTERRUPT 1FH (LOCATION 0007CH) TO
  4114                              <1> ;  POINT TO THE USER SUPPLIED TABLE OF GRAPHIC IMAGES (8X8 BOXES).
  4115                              <1> ;  FAILURE TO DO SO WILL CAUSE IN STRANGE RESULTS
  4116                              <1> ;-----------------------------------------------------
  4117                              <1> 
  4118                              <1> GRAPHICS_WRITE:
  4119 000027F9 25FF000000          <1> 	and 	eax, 0FFh		; ZERO TO HIGH OF CODE POINT
  4120 000027FE 50                  <1> 	PUSH	eAX			; SAVE CODE POINT VALUE
  4121                              <1> 
  4122                              <1> ;-----	DETERMINE POSITION IN REGEN BUFFER TO PUT CODE POINTS
  4123                              <1> 
  4124 000027FF E84D010000          <1> 	CALL	S26			; FIND LOCATION IN REGEN BUFFER
  4125 00002804 89C7                <1> 	MOV	eDI, eAX		; REGEN POINTER IN DI
  4126                              <1> 
  4127                              <1> ;-----	DETERMINE REGION TO GET CODE POINTS FROM
  4128                              <1> 
  4129 00002806 58                  <1> 	POP	eAX			; RECOVER CODE POINT
  4130                              <1> 
  4131 00002807 BE[A0320100]        <1> 	MOV	eSI, CRT_CHAR_GEN	; OFFSET OF IMAGES
  4132                              <1> 
  4133                              <1> ;-----	DETERMINE GRAPHICS MODE IN OPERATION
  4134                              <1> 					; DETERMINE_MODE
  4135 0000280C 66C1E003            <1> 	SAL	AX, 3			; MULTIPLY CODE POINT VALUE BY 8
  4136 00002810 01C6                <1> 	ADD	eSI, eAX		; SI HAS OFFSET OF DESIRED CODES
  4137                              <1> 	
  4138 00002812 803D[7A660000]06    <1> 	CMP	byte [CRT_MODE], 6
  4139 00002819 7231                <1> 	JC	short S6		; TEST FOR MEDIUM RESOLUTION MODE
  4140                              <1> 
  4141                              <1> ;-----	HIGH RESOLUTION MODE
  4142                              <1> 
  4143 0000281B 81C700800B00        <1> 	add	edi, 0B8000h
  4144                              <1> S1:					; HIGH_CHAR
  4145 00002821 57                  <1> 	PUSH	eDI			; SAVE REGEN POINTER
  4146 00002822 56                  <1> 	PUSH	eSI			; SAVE CODE POINTER
  4147 00002823 B604                <1> 	MOV	DH, 4			; NUMBER OF TIMES THROUGH LOOP
  4148                              <1> S2:
  4149 00002825 AC                  <1> 	LODSB				; GET BYTE FROM CODE POINTS
  4150 00002826 F6C380              <1> 	TEST	BL, 80H			; SHOULD WE USE THE FUNCTION
  4151 00002829 7515                <1> 	JNZ	short S5		; TO PUT CHAR IN
  4152 0000282B AA                  <1> 	STOSB				; STORE IN REGEN BUFFER
  4153 0000282C AC                  <1> 	LODSB
  4154                              <1> S4:
  4155 0000282D 8887FF1F0000        <1> 	MOV	[eDI+2000H-1], AL ; STORE IN SECOND HALF
  4156 00002833 83C74F              <1> 	ADD	eDI, 79			; MOVE TO NEXT ROW IN REGEN
  4157 00002836 FECE                <1> 	DEC	DH			; DONE WITH LOOP
  4158 00002838 75EB                <1> 	JNZ	short S2
  4159 0000283A 5E                  <1> 	POP	eSI
  4160 0000283B 5F                  <1> 	POP	eDI			; RECOVER REGEN POINTER
  4161 0000283C 47                  <1> 	INC	eDI			; POINT TO NEXT CHAR POSITION
  4162 0000283D E2E2                <1> 	LOOP	S1			; MORE CHARS TO WRITE
  4163 0000283F C3                  <1> 	retn
  4164                              <1> 
  4165                              <1> S5:
  4166 00002840 3207                <1> 	XOR	AL, [eDI]		; EXCLUSIVE OR WITH CURRENT
  4167 00002842 AA                  <1> 	STOSB				; STORE THE CODE POINT
  4168 00002843 AC                  <1> 	LODSB				; AGAIN FOR ODD FIELD
  4169 00002844 3287FF1F0000        <1> 	XOR	AL, [eDI+2000H-1]
  4170 0000284A EBE1                <1> 	JMP	short S4		; BACK TO MAINSTREAM
  4171                              <1> 
  4172                              <1> ;-----	MEDIUM RESOLUTION WRITE
  4173                              <1> S6:					; MED_RES_WRITE
  4174 0000284C 88DA                <1> 	MOV	DL, BL			; SAVE HIGH COLOR BIT
  4175 0000284E 66D1E7              <1> 	SAL	DI, 1			; OFFSET*2 SINCE 2 BYTES/CHAR
  4176                              <1> 					; EXPAND BL TO FULL WORD OF COLOR
  4177 00002851 80E303              <1> 	AND	BL, 3			; ISOLATE THE COLOR BITS ( LOW 2 BITS )
  4178 00002854 B055                <1> 	MOV	AL, 055H 		; GET BIT CONVERSION MULTIPLIER
  4179 00002856 F6E3                <1> 	MUL	BL			; EXPAND 2 COLOR BITS TO 4 REPLICATIONS
  4180 00002858 88C3                <1> 	MOV	BL, AL			; PLACE BACK IN WORK REGISTER
  4181 0000285A 88C7                <1> 	MOV	BH, AL			; EXPAND TO 8 REPLICATIONS OF COLOR BITS
  4182 0000285C 81C700800B00        <1> 	add	edi, 0B8000h
  4183                              <1> S7:                                     ; MED_CHAR
  4184 00002862 57                  <1> 	PUSH	eDI			; SAVE REGEN POINTER
  4185 00002863 56                  <1> 	PUSH	eSI			; SAVE THE CODE POINTER
  4186 00002864 B604                <1> 	MOV	DH, 4			; NUMBER OF LOOPS
  4187                              <1> S8:
  4188 00002866 AC                  <1> 	LODSB				; GET CODE POINT
  4189 00002867 E8B3000000          <1> 	CALL	S21			; DOUBLE UP ALL THE BITS
  4190 0000286C 6621D8              <1> 	AND	AX, BX			; CONVERT TO FOREGROUND COLOR ( 0 BACK )
  4191 0000286F 86E0                <1> 	XCHG	AH, AL			; SWAP HIGH/LOW BYTES FOR WORD MOVE
  4192 00002871 F6C280              <1> 	TEST	DL, 80H			; IS THIS XOR FUNCTION
  4193 00002874 7403                <1> 	JZ	short S9		; NO, STORE IT IN AS IS
  4194 00002876 663307              <1> 	XOR	AX, [eDI]		; DO FUNCTION WITH LOW/HIGH
  4195                              <1> S9:
  4196 00002879 668907              <1> 	MOV	[eDI], AX		; STORE FIRST BYTE HIGH, SECOND LOW
  4197 0000287C AC                  <1> 	LODSB				; GET CODE POINT
  4198 0000287D E89D000000          <1> 	CALL	S21
  4199 00002882 6621D8              <1> 	AND	AX, BX			; CONVERT TO COLOR
  4200 00002885 86E0                <1> 	XCHG	AH, AL			; SWAP HIGH/LOW BYTES FOR WORD MOVE
  4201 00002887 F6C280              <1> 	TEST	DL, 80H			; AGAIN, IS THIS XOR FUNCTION
  4202 0000288A 7407                <1> 	JZ	short _S10		; NO, JUST STORE THE VALUES
  4203 0000288C 66338700200000      <1> 	XOR	AX, [eDI+2000H]		; FUNCTION WITH FIRST HALF LOW
  4204                              <1> _S10:
  4205 00002893 66898700200000      <1> 	MOV	[eDI+2000H], AX		; STORE SECOND PORTION HIGH
  4206 0000289A 6683C750            <1> 	ADD	DI, 80			; POINT TO NEXT LOCATION
  4207 0000289E FECE                <1> 	DEC	DH
  4208 000028A0 75C4                <1> 	JNZ	short S8		; KEEP GOING
  4209 000028A2 5E                  <1> 	POP	eSI			; RECOVER CODE POINTER
  4210 000028A3 5F                  <1> 	POP	eDI			; RECOVER REGEN POINTER
  4211 000028A4 47                  <1> 	INC	eDI			; POINT TO NEXT CHAR POSITION
  4212 000028A5 47                  <1> 	INC	eDI
  4213 000028A6 E2BA                <1> 	LOOP	S7			; MORE TO WRITE
  4214 000028A8 C3                  <1> 	retn
  4215                              <1> 
  4216                              <1> ; 04/07/2016
  4217                              <1> ; 01/07/2016
  4218                              <1> ; 30/06/2016 - TRDOS 386 (TRDOS v2.0)
  4219                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4220                              <1> ;----------------------------------------
  4221                              <1> ; GRAPHICS READ
  4222                              <1> ;----------------------------------------
  4223                              <1> GRAPHICS_READ:
  4224 000028A9 E8A3000000          <1> 	CALL	S26			; CONVERTED TO OFFSET IN REGEN
  4225 000028AE 89C6                <1> 	MOV	eSI, eAX		; SAVE IN SI
  4226 000028B0 81C600800B00        <1> 	add	esi, 0B8000h		; 01/07/2016
  4227 000028B6 83EC08              <1> 	SUB	eSP, 8			; ALLOCATE SPACE FOR THE READ CODE POINT
  4228 000028B9 89E5                <1> 	MOV	eBP, eSP		; POINTER TO SAVE AREA
  4229                              <1> 
  4230                              <1> ;-----	DETERMINE GRAPHICS MODES
  4231 000028BB B604                <1> 	mov	dh, 4			; number of passes ; 01/07/2016
  4232 000028BD 803D[7A660000]06    <1> 	CMP	byte [CRT_MODE], 6
  4233 000028C4 7219                <1> 	JC	short S12		; MEDIUM RESOLUTION
  4234                              <1> 
  4235                              <1> ;-----	HIGH RESOLUTION READ
  4236                              <1> ;-----	GET VALUES FROM REGEN BUFFER AND CONVERT TO CODE POINT
  4237                              <1> 	;MOV	DH,4			; NUMBER OF PASSES
  4238                              <1> S11:
  4239 000028C6 8A06                <1> 	MOV	AL, [eSI] 		; GET FIRST BYTE
  4240 000028C8 884500              <1> 	MOV	[eBP], AL 		; SAVE IN STORAGE AREA
  4241 000028CB 45                  <1> 	INC	eBP			; NEXT LOCATION
  4242 000028CC 8A8600200000        <1> 	MOV	AL, [eSI+2000H]		; GET LOWER REGION BYTE
  4243 000028D2 884500              <1> 	MOV	[eBP], AL 		; ADJUST AND STORE
  4244 000028D5 45                  <1> 	INC	eBP
  4245 000028D6 83C650              <1> 	ADD	eSI, 80			; POINTER INTO REGEN
  4246 000028D9 FECE                <1> 	DEC	DH			; LOOP CONTROL
  4247 000028DB 75E9                <1> 	JNZ	short S11		; DO IT SOME MORE
  4248 000028DD EB1D                <1> 	JMP	SHORT S14		; GO MATCH THE SAVED CODE POINTS
  4249                              <1> 
  4250                              <1> ;-----	MEDIUM RESOLUTION READ
  4251                              <1> S12:	
  4252 000028DF 66D1E6              <1> 	SAL	SI, 1			; OFFSET*2 SINCE 2 BYTES/CHAR
  4253                              <1> 	;MOV	DH, 4			; NUMBER OF PASSES
  4254                              <1> S13:
  4255 000028E2 E84D000000          <1> 	CALL	S23			; GET BYTES FROM REGEN INTO SINGLE SAVE
  4256 000028E7 81C6FE1F0000        <1> 	ADD	eSI, 2000H-2		; GO TO LOWER REGION
  4257 000028ED E842000000          <1> 	CALL	S23			; GET THIS PAIR INTO SAVE
  4258 000028F2 81EEB21F0000        <1> 	SUB	eSI, 2000H-80+2		; ADJUST POINTER BACK INTO UPPER
  4259 000028F8 FECE                <1> 	DEC	DH
  4260 000028FA 75E6                <1> 	JNZ	short S13		; KEEP GOING UNTIL ALL 8 DONE
  4261                              <1> 
  4262                              <1> ;-----	SAVE AREA HAS CHARACTER IN IT, MATCH IT
  4263                              <1> S14:					; FIND_CHAR
  4264 000028FC BF[A0320100]        <1> 	MOV	eDI, CRT_CHAR_GEN	; ESTABLISH ADDRESSING
  4265 00002901 83ED08              <1> 	SUB	eBP, 8			; ADJUST POINTER TO START OF SAVE AREA
  4266 00002904 89EE                <1> 	MOV	eSI, eBP
  4267                              <1> S15:
  4268 00002906 66B80001            <1> 	mov	ax, 256			; NUMBER TO TEST AGAINST
  4269                              <1> S16:
  4270 0000290A 56                  <1> 	PUSH	eSI			; SAVE SAVE AREA POINTER
  4271 0000290B 57                  <1> 	PUSH	eDI			; SAVE CODE POINTER
  4272                              <1> 	;MOV	eCX, 4			; NUMBER OF WORDS TO MATCH
  4273                              <1> 	;REPE	CMPSW			; COMPARE THE 8 BYTES AS WORDS
  4274 0000290C A7                  <1> 	cmpsd				; compare first 4 bytes 
  4275 0000290D 7501                <1> 	jne	short S17		; 
  4276 0000290F A7                  <1> 	cmpsd				; compare last 4 bytes
  4277                              <1> S17:
  4278 00002910 5F                  <1> 	POP	eDI			; RECOVER THE POINTERS
  4279 00002911 5E                  <1> 	POP	eSI
  4280                              <1> 	;JZ	short S18		; IF ZERO FLAG SET, THEN MATCH OCCURRED
  4281 00002912 7407                <1> 	je	short S18
  4282                              <1> 	;				; NO MATCH, MOVE ON TO NEXT
  4283 00002914 83C708              <1> 	ADD	eDI, 8			; NEXT CODE POINT
  4284 00002917 6648                <1> 	dec	ax			; LOOP CONTROL
  4285 00002919 75EF                <1> 	JNZ	short S16		; DO ALL OF THEM
  4286                              <1> 
  4287                              <1> ;-----	CHARACTER IS FOUND ( AL=0 IF NOT FOUND )
  4288                              <1> S18:	
  4289 0000291B 83C408              <1> 	ADD	eSP, 8			; READJUST THE STACK, THROW AWAY SAVE
  4290 0000291E C3                  <1> 	retn				; ALL DONE
  4291                              <1> 
  4292                              <1> ; 30/06/2016 - TRDOS 386 (TRDOS v2.0)
  4293                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4294                              <1> ;--------------------------------------------
  4295                              <1> ; EXPAND BYTE
  4296                              <1> ;  THIS ROUTINE TAKES THE BYTE IN AL AND DOUBLES ALL
  4297                              <1> ;  OF THE BITS, TURNING THE 8 BITS INTO 16 BITS.
  4298                              <1> ;  THE RESULT IS LEFT IN AX
  4299                              <1> ;--------------------------------------------
  4300                              <1> S21:
  4301 0000291F 6651                <1> 	PUSH	CX			; SAVE REGISTER
  4302                              <1> 	;MOV	CX, 8			; SHIFT COUNT REGISTER FOR ONE BYTE
  4303 00002921 B108                <1> 	mov	cl, 8
  4304                              <1> S22:
  4305 00002923 D0C8                <1> 	ROR	AL,1			; SHIFT BITS, LOW BIT INTO CARRY FLAG
  4306 00002925 66D1DD              <1> 	RCR	BP,1			; MOVE CARRY FLAG (LOW BIT INTO RESULTS
  4307 00002928 66D1FD              <1> 	SAR	BP,1			; SIGN EXTEND HIGH BIT (DOUBLE IT)
  4308                              <1> 	;LOOP	S22			; REPEAT FOR ALL 8 BITS
  4309 0000292B FEC9                <1> 	dec	cl
  4310 0000292D 75F4                <1> 	jnz	short S22
  4311 0000292F 6695                <1> 	XCHG	AX, BP			; MOVE RESULTS TO PARAMETER REGISTER
  4312 00002931 6659                <1> 	POP	CX			; RECOVER REGISTER
  4313 00002933 C3                  <1> 	RETn				; ALL DONE
  4314                              <1> 
  4315                              <1> ; 01/07/2016 - TRDOS 386 (TRDOS v2.0)
  4316                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4317                              <1> ;--------------------------------------------------
  4318                              <1> ; MED_READ_BYTE
  4319                              <1> ; THIS ROUTINE WILL TAKE 2 BYTES FROM THE REGEN BUFFER,
  4320                              <1> ;  COMPARE AGAINST THE CURRENT FOREGROUND COLOR, AND PLACE
  4321                              <1> ;  THE CORRESPONDING ON/OFF BIT PATTERN INTO THE CURRENT
  4322                              <1> ;  POSITION IN THE SAVE AREA
  4323                              <1> ; ENTRY --
  4324                              <1> ;  SI,DS = POINTER TO REGEN AREA OF INTEREST
  4325                              <1> ;  BX = EXPANDED FOREGROUND COLOR
  4326                              <1> ;  BP = POINTER TO SAVE AREA
  4327                              <1> ; EXIT --
  4328                              <1> ;  SI AND BP ARE INCREMENTED
  4329                              <1> ;----------------------------------------------------
  4330                              <1> S23:
  4331 00002934 66AD                <1> 	LODSW				; GET FIRST BYTE AND SECOND BYTES
  4332 00002936 86C4                <1> 	XCHG	AL, AH			; SWAP FOR COMPARE
  4333 00002938 66B900C0            <1> 	MOV	CX, 0C000H		; 2 BIT MASK TO TEST THE ENTRIES
  4334 0000293C B200                <1> 	MOV	DL, 0			; RESULT REGISTER
  4335                              <1> S24:
  4336 0000293E 6685C8              <1> 	TEST	AX, CX			; IS THIS SECTION BACKCROUND?
  4337 00002941 7401                <1>         JZ      short S25               ; IF ZERO, IT IS BACKGROUND (CARRY=0)
  4338 00002943 F9                  <1> 	STC				; WASN'T, SO SET CARRY
  4339                              <1> S25:
  4340 00002944 D0D2                <1> 	RCL	DL, 1			; MOVE THAT BIT INTO THE RESULT
  4341 00002946 66C1E902            <1> 	SHR	CX, 2			; MOVE THE MASK TO THE RIGHT BY 2 BITS
  4342 0000294A 73F2                <1> 	JNC	short S24		; DO IT AGAIN IF MASK DIDN'T FALL OUT
  4343 0000294C 885500              <1> 	MOV	[eBP], DL 		; STORE RESULT IN SAVE AREA
  4344 0000294F 45                  <1> 	INC	eBP			; ADJUST POINTER
  4345 00002950 C3                  <1> 	RETn				; ALL DONE
  4346                              <1> 
  4347                              <1> ; 30/06/2016 - TRDOS 386 (TRDOS v2.0)
  4348                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4349                              <1> ;-----------------------------------------
  4350                              <1> ; V4_POSITION
  4351                              <1> ;  THIS ROUTINE TAKES THE CURSOR POSITION CONTAINED IN
  4352                              <1> ;  THE MEMORY LOCATION, AND CONVERTS IT INTO AN OFFSET
  4353                              <1> ;  INTO THE REGEN BUFFER, ASSUMING ONE BYTE/CHAR.
  4354                              <1> ;  FOR MEDIUM RESOLUTION GRAPHICS, THE NUMBER MUST
  4355                              <1> ;  BE DOUBLED.
  4356                              <1> ; ENTRY -- NO REGISTERS,MEMORY LOCATION @CURSOR_POSN IS USED
  4357                              <1> ; EXIT--
  4358                              <1> ;  AX CONTAINS OFFSET INTO REGEN BUFFER
  4359                              <1> ;-----------------------------------------
  4360                              <1> S26:
  4361 00002951 0FB705[9E5E0100]    <1> 	movzx	eax, word [CURSOR_POSN]	; GET CURRENT CURSOR
  4362                              <1> GRAPH_POSN:
  4363 00002958 53                  <1> 	PUSH	eBX			; SAVE REGISTER
  4364 00002959 0FB6D8              <1> 	movzx	ebx, al			; SAVE A COPY OF CURRENT CURSOR
  4365 0000295C A0[7C660000]        <1> 	MOV	AL, [CRT_COLS]		; GET BYTES PER COLUMN
  4366 00002961 F6E4                <1> 	MUL	AH			; MULTIPLY BY ROWS
  4367 00002963 66C1E002            <1> 	SHL	AX, 2			; MULTIPLY * 4 SINCE 4 ROWS/BYTE
  4368 00002967 01D8                <1> 	ADD	eAX, eBX		; DETERMINE OFFSET
  4369 00002969 5B                  <1> 	POP	eBX			; RECOVER POINTER
  4370 0000296A C3                  <1> 	RETn				; ALL DONE
  4371                              <1> 
  4372                              <1> ; 09/07/2016
  4373                              <1> ; 01/07/2016 - TRDOS 386 (TRDOS v2.0)
  4374                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4375                              <1> ;---------------------------------------------
  4376                              <1> ; SET_COLOR
  4377                              <1> ;	THIS ROUTINE WILL ESTABLISH THE BACKGROUND COLOR, THE OVERSCAN COLOR,
  4378                              <1> ;	AND THE FOREGROUND COLOR SET FOR MEDIUM RESOLUTION GRAPHICS
  4379                              <1> ; INPUT
  4380                              <1> ;	(BH) HAS COLOR ID
  4381                              <1> ;		IF BH=0, THE BACKGROUND COLOR VALUE IS SET
  4382                              <1> ;			FROM THE LOW BITS OF BL (0-31)
  4383                              <1> ;		IF BH=1, THE PALETTE SELECTION IS MADE
  4384                              <1> ;			BASED ON THE LOW BIT OF BL:
  4385                              <1> ;				0 = GREEN, RED, YELLOW FOR COLORS 1,2,3
  4386                              <1> ;				1 = BLUE, CYAN, MAGENTA FOR COLORS 1,2,3
  4387                              <1> ;	(BL) HAS THE COLOR VALUE TO BE USED
  4388                              <1> ; OUTPUT
  4389                              <1> ;	THE COLOR SELECTION IS UPDATED
  4390                              <1> ;----------------------------------------------
  4391                              <1> SET_COLOR:
  4392 0000296B 803D[7A660000]07    <1>         cmp     byte [CRT_MODE], 7      ; 09/07/2016
  4393 00002972 0F87DEEFFFFF        <1> 	ja	VIDEO_RETURN		; nothing to do for VGA modes	 
  4394                              <1> 
  4395                              <1> 	;MOV	DX, [ADDR_6845]		; I/O PORT FOR PALETTE
  4396                              <1> 	;mov	dx, 3D4h
  4397                              <1> 	;ADD	DX,5			; OVERSCAN PORT
  4398 00002978 66BAD903            <1> 	mov	dx, 3D9h
  4399 0000297C A0[7D660000]        <1> 	MOV	AL, [CRT_PALETTE] 	; GET THE CURRENT PALETTE VALUE
  4400 00002981 08FF                <1> 	OR	BH, BH			; IS THIS COLOR 0?
  4401 00002983 7512                <1> 	JNZ	short M20		; OUTPUT COLOR 1
  4402                              <1> 
  4403                              <1> ;-----	HANDLE COLOR 0 BY SETTING THE BACKGROUND COLOR
  4404                              <1> 
  4405 00002985 24E0                <1> 	AND	AL, 0E0H 		; TURN OFF LOW 5 BITS OF CURRENT
  4406 00002987 80E31F              <1> 	AND	BL, 01FH 		; TURN OFF HIGH 3 BITS OF INPUT VALUE
  4407 0000298A 08D8                <1> 	OR	AL, BL			; PUT VALUE INTO REGISTER
  4408                              <1> M19:					; OUTPUT THE PALETTE
  4409 0000298C EE                  <1> 	OUT	DX, AL			; OUTPUT COLOR SELECTION TO 3D9 PORT
  4410 0000298D A2[7D660000]        <1> 	MOV	[CRT_PALETTE], AL 	; SAVE THE COLOR VALUE
  4411 00002992 E9BFEFFFFF          <1> 	JMP	VIDEO_RETURN
  4412                              <1> 
  4413                              <1> ;-----	HANDLE COLOR 1 BY SELECTING THE PALETTE TO BE USED
  4414                              <1> 
  4415                              <1> M20:
  4416 00002997 24DF                <1> 	AND	AL, 0DFH 		; TURN OFF PALETTE SELECT BIT
  4417 00002999 D0EB                <1> 	SHR	BL, 1			; TEST THE LOW ORDER BIT OF BL
  4418 0000299B 73EF                <1> 	JNC	short M19		; ALREADY DONE
  4419 0000299D 0C20                <1> 	OR	AL, 20H			; TURN ON PALETTE SELECT BIT
  4420 0000299F EBEB                <1> 	JMP	short M19		; GO DO IT
  4421                              <1> 
  4422                              <1> ; 09/07/2016
  4423                              <1> ; 01/07/2016 - TRDOS 386 (TRDOS v2.0)
  4424                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4425                              <1> ;--------------------------------------------
  4426                              <1> ; READ DOT -- WRITE DOT
  4427                              <1> ; THESE ROUTINES WILL WRITE A DOT, OR READ THE
  4428                              <1> ;  DOT AT THE INDICATED LOCATION
  4429                              <1> ; ENTRY --
  4430                              <1> ;   DX = ROW (0-199)	(THE ACTUAL VALUE DEPENDS ON THE MODE)
  4431                              <1> ;   CX = COLUMN ( 0-639) ( THE VALUES ARE NOT RANGE CHECKED )
  4432                              <1> ;   AL = DOT VALUE TO WRITE (1,2 OR 4 BITS DEPENDING ON MODE,
  4433                              <1> ;	REQUIRED FOR WRITE DOT ONLY, RIGHT JUSTIFIED)
  4434                              <1> ;	BIT 7 OF AL = 1 INDICATES XOR THE VALUE INTO THE LOCATION
  4435                              <1> ;   DS = DATA SEGMENT
  4436                              <1> ;   ES = REGEN SEGMENT
  4437                              <1> ;
  4438                              <1> ; EXIT
  4439                              <1> ;	AL = DOT VALUE READ, RIGHT JUSTIFIED, READ ONLY
  4440                              <1> ;----------------------------------------------
  4441                              <1> 
  4442                              <1> READ_DOT:
  4443                              <1> 	; 09/07/2016
  4444 000029A1 8A25[7A660000]      <1> 	mov	ah,  [CRT_MODE]
  4445 000029A7 80FC07              <1> 	cmp	ah, 7 ; 6!?
  4446 000029AA 760A                <1> 	jna	short read_dot_cga
  4447                              <1> 
  4448 000029AC E8CB030000          <1> 	call	vga_read_pixel
  4449                              <1> 	; al = pixel value
  4450 000029B1 E9A5EFFFFF          <1> 	jmp	_video_return
  4451                              <1> 
  4452                              <1> read_dot_cga:
  4453                              <1> 	;je	VIDEO_RETURN ; 7	
  4454 000029B6 80FC04              <1> 	cmp	ah, 4 ; graphics ? 
  4455 000029B9 0F8297EFFFFF        <1> 	jb	VIDEO_RETURN ; no, text mode, nothing to do
  4456                              <1> 
  4457 000029BF E855000000          <1> 	CALL	R3			; DETERMINE BYTE POSITION OF DOT
  4458 000029C4 8A06                <1> 	MOV	AL, [eSI]		; GET THE BYTE
  4459 000029C6 20E0                <1> 	AND	AL, AH			; MASK OFF THE OTHER BITS IN THE BYTE
  4460 000029C8 D2E0                <1> 	SHL	AL, CL			; LEFT JUSTIFY THE VALUE
  4461 000029CA 88F1                <1> 	MOV	CL, DH			; GET NUMBER OF BITS IN RESULT
  4462 000029CC D2C0                <1> 	ROL	AL, CL			; RIGHT JUSTIFY THE RESULT
  4463                              <1> 	;JMP	VIDEO_RETURN		; RETURN FROM VIDEO I/O
  4464 000029CE 0FB6C0              <1> 	movzx	eax, al
  4465 000029D1 E985EFFFFF          <1> 	jmp	_video_return
  4466                              <1> 
  4467                              <1> ; 09/07/2016
  4468                              <1> ; 01/07/2016 - TRDOS 386 (TRDOS v2.0)
  4469                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4470                              <1> 
  4471                              <1> WRITE_DOT:
  4472                              <1> 	; 09/07/2016
  4473 000029D6 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE]
  4474 000029DC 80FC07              <1> 	cmp	ah, 7 ; 6!?
  4475 000029DF 760A                <1> 	jna	short write_dot_cga
  4476                              <1> 	
  4477 000029E1 E805030000          <1> 	call	vga_write_pixel
  4478 000029E6 E96BEFFFFF          <1> 	jmp	VIDEO_RETURN
  4479                              <1> 
  4480                              <1> write_dot_cga:
  4481                              <1> 	;je	VIDEO_RETURN ; 7	
  4482 000029EB 80FC04              <1> 	cmp	ah, 4 ; graphics ? 
  4483 000029EE 0F8262EFFFFF        <1> 	jb	VIDEO_RETURN ; no, text mode, nothing to do
  4484                              <1> 
  4485                              <1> 	;PUSH	AX			; SAVE DOT VALUE
  4486 000029F4 6650                <1> 	PUSH	AX			; TWICE
  4487 000029F6 E81E000000          <1> 	CALL	R3			; DETERMINE BYTE POSITION OF THE DOT
  4488 000029FB D2E8                <1> 	SHR	AL, CL			; SHIFT TO SET UP THE BITS FOR OUTPUT
  4489 000029FD 20E0                <1> 	AND	AL, AH			; STRIP OFF THE OTHER BITS
  4490 000029FF 8A0E                <1> 	MOV	CL, [eSI]		; GET THE CURRENT BYTE
  4491 00002A01 665B                <1> 	POP	BX			; RECOVER XOR FLAG
  4492 00002A03 F6C380              <1> 	TEST	BL, 80H			; IS IT ON
  4493 00002A06 750D                <1> 	JNZ	short R2		; YES, XOR THE DOT
  4494 00002A08 F6D4                <1> 	NOT	AH			; SET MASK TO REMOVE THE INDICATED BITS
  4495 00002A0A 20E1                <1> 	AND	CL, AH
  4496 00002A0C 08C8                <1> 	OR	AL, CL			; OR IN THE NEW VALUE OF THOSE BITS
  4497                              <1> R1:					; FINISH_DOT
  4498 00002A0E 8806                <1> 	MOV	[eSI], AL		; RESTORE THE BYTE IN MEMORY
  4499                              <1> 	;POP	AX
  4500 00002A10 E941EFFFFF          <1> 	JMP	VIDEO_RETURN		; RETURN FROM VIDEO I/O
  4501                              <1> R2:					; XOR_DOT
  4502 00002A15 30C8                <1> 	XOR	AL, CL			; EXCLUSIVE OR THE DOTS
  4503 00002A17 EBF5                <1> 	JMP	short R1		; FINISH UP THE WRITING
  4504                              <1> 
  4505                              <1> ; 01/07/2016 - TRDOS 386 (TRDOS v2.0)
  4506                              <1> ; VIDEO1.ASM - 24/03/1985 (IBM PC-AT BIOS source code)
  4507                              <1> 
  4508                              <1> ;----------------------------------------------
  4509                              <1> ; THIS SUBROUTINE DETERMINES THE REGEN BYTE LOCATION OF THE
  4510                              <1> ; INDICATED ROW COLUMN VALUE IN GRAPHICS MODE.
  4511                              <1> ; ENTRY --
  4512                              <1> ;  DX = ROW VALUE (0-199)
  4513                              <1> ;  CX = COLUMN VALUE (0-639)
  4514                              <1> ; EXIT --
  4515                              <1> ;  SI = OFFSET INTO REGEN BUFFER FOR BYTE OF INTEREST
  4516                              <1> ;  AH = MASK TO STRIP OFF THE BITS OF INTEREST
  4517                              <1> ;  CL = BITS TO SHIFT TO RIGHT JUSTIFY THE MASK IN AH
  4518                              <1> ;  DH = # BITS IN RESULT
  4519                              <1> ;  BX = MODIFIED
  4520                              <1> ;-----------------------------------------------
  4521                              <1> R3:
  4522                              <1> 
  4523                              <1> ;-----	DETERMINE 1ST BYTE IN INDICATED ROW BY MULTIPLYING ROW VALUE BY 40
  4524                              <1> ;-----	 ( LOW BIT OF ROW DETERMINES EVEN/ODD, 80 BYTES/ROW )
  4525                              <1> 
  4526 00002A19 0FB7F0              <1> 	movzx	esi, ax			; WILL SAVE AL AND AH DURING OPERATION
  4527 00002A1C B028                <1> 	MOV	AL, 40
  4528 00002A1E F6E2                <1> 	MUL	DL			; AX= ADDRESS OF START OF INDICATED ROW
  4529 00002A20 A808                <1> 	TEST	AL, 08H 		; TEST FOR EVEN/ODD ROW CALCULATED
  4530 00002A22 7404                <1> 	JZ	short R4		; JUMP IF EVEN ROW
  4531 00002A24 6605D81F            <1> 	ADD	AX, 2000H-40		; OFFSET TO LOCATION OF ODD ROWS ADJUST
  4532                              <1> R4:					; EVEN_ROW
  4533 00002A28 6696                <1> 	XCHG	SI, AX			; MOVE POINTER TO (SI) AND RECOVER (AX)
  4534 00002A2A 81C600800B00        <1> 	add	esi, 0B8000h
  4535 00002A30 6689CA              <1> 	MOV	DX, CX			; COLUMN VALUE TO DX
  4536                              <1> 
  4537                              <1> ;-----	DETERMINE GRAPHICS MODE CURRENTLY IN EFFECT
  4538                              <1> 
  4539                              <1> ; SET UP THE REGISTERS ACCORDING TO THE MODE
  4540                              <1> ; CH = MASK FOR LOW OF COLUMN ADDRESS ( 7/3 FOR HIGH/MED RES )
  4541                              <1> ; CL = # OF ADDRESS BITS IN COLUMN VALUE ( 3/2 FOR H/M )
  4542                              <1> ; BL = MASK TO SELECT BITS FROM POINTED BYTE ( 80H/C0H FOR H/M )
  4543                              <1> ; BH = NUMBER OF VALID BITS IN POINTED BYTE ( 1/2 FOR H/M )
  4544                              <1> 
  4545 00002A33 66BBC002            <1> 	MOV	BX, 2C0H
  4546 00002A37 66B90203            <1> 	MOV	CX, 302H 		; SET PARMS FOR MED RES
  4547 00002A3B 803D[7A660000]06    <1> 	CMP	byte [CRT_MODE], 6
  4548 00002A42 7208                <1> 	JC	short R5		; HANDLE IF MED RES
  4549 00002A44 66BB8001            <1> 	MOV	BX, 180H
  4550 00002A48 66B90307            <1> 	MOV	CX, 703H 		; SET PARMS FOR HIGH RES
  4551                              <1> 
  4552                              <1> ;-----	DETERMINE BIT OFFSET IN BYTE FROM COLUMN MASK
  4553                              <1> R5:
  4554 00002A4C 20D5                <1> 	AND	CH, DL			; ADDRESS OF PEL WITHIN BYTE TO CH
  4555                              <1> 
  4556                              <1> ;-----	DETERMINE BYTE OFFSET FOR THIS LOCATION IN COLUMN
  4557                              <1> 
  4558 00002A4E 66D3EA              <1> 	SHR	DX, CL			; SHIFT BY CORRECT AMOUNT
  4559 00002A51 6601D6              <1> 	ADD	SI, DX			; INCREMENT THE POINTER
  4560 00002A54 88FE                <1> 	MOV	DH, BH			; GET THE # OF BITS IN RESULT TO DH
  4561                              <1> 
  4562                              <1> ;-----	MULTIPLY BH (VALID BITS IN BYTE) BY CH (BIT OFFSET)
  4563                              <1> 
  4564 00002A56 28C9                <1> 	SUB	CL, CL			; ZERO INTO STORAGE LOCATION
  4565                              <1> R6:
  4566 00002A58 D0C8                <1> 	ROR	AL, 1			; LEFT JUSTIFY VALUE IN AL (FOR WRITE)
  4567 00002A5A 00E9                <1> 	ADD	CL, CH			; ADD IN THE BIT OFFSET VALUE
  4568 00002A5C FECF                <1> 	DEC	BH			; LOOP CONTROL
  4569 00002A5E 75F8                <1> 	JNZ	short R6		; ON EXIT, CL HAS COUNT TO RESTORE BITS
  4570 00002A60 88DC                <1> 	MOV	AH, BL			;  GET MASK TO AH
  4571 00002A62 D2EC                <1> 	SHR	AH, CL			;  MOVE THE MASK TO CORRECT LOCATION
  4572 00002A64 C3                  <1> 	RETn				;  RETURN WITH EVERYTHING SET UP
  4573                              <1> 
  4574                              <1> load_dac_palette:
  4575                              <1> 	; 29/07/2016
  4576                              <1> 	; 23/07/2016
  4577                              <1> 	; 03/07/2016 (TRDOS 386 = TRDOS v2.0)
  4578                              <1> 	; (set_mode_vga)
  4579                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  4580                              <1> 	; vgabios-0.7a (2011)
  4581                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  4582                              <1> 	; 'vgabios.c', 'load_dac_palette'
  4583                              <1> 	;
  4584                              <1> 	; Oracle VirtualBox 5.0.24 VGABios Source Code
  4585                              <1> 	; ('vgabios.c', 'vgatables.h', 'vgafonts.h', 'vgarom.asm')
  4586                              <1> 	;
  4587                              <1> 	; INPUT -> AH = DAC selection number (3, 2 or 1)
  4588                              <1> 	; OUTPUT -> ECX = 0, AX = 0
  4589                              <1> 	; (Modifed registers: EAX, ECX, EDX, ESI)
  4590                              <1> 	;
  4591 00002A65 66BAC803            <1> 	mov	dx, 3C8h  ; VGAREG_DAC_WRITE_ADDRESS
  4592 00002A69 28C0                <1> 	sub	al, al ; 0
  4593 00002A6B EE                  <1> 	out	dx, al ; 0 ; color index, always 0 at the beginning	
  4594 00002A6C 6642                <1> 	inc	dx   ; 3C9h ; VGAREG_DAC_DATA
  4595 00002A6E B900010000          <1> 	mov	ecx, 256   ; always 256*3 values
  4596                              <1> 	;push	esi
  4597 00002A73 88E0                <1> 	mov	al, ah
  4598 00002A75 B43F                <1> 	mov	ah, 3Fh	; 3Fh except DAC selection number 3
  4599 00002A77 3C02                <1> 	cmp 	al, 2
  4600 00002A79 7414                <1> 	je	short l_dac_p_2
  4601 00002A7B 7719                <1> 	ja	short l_dac_p_3
  4602 00002A7D 20C0                <1> 	and	al, al
  4603 00002A7F 7507                <1> 	jnz	short l_dac_p_1
  4604                              <1> l_dac_p_0:
  4605 00002A81 BE[602D0100]        <1> 	mov	esi, palette0
  4606 00002A86 EB15                <1> 	jmp	short l_dac_p_4	
  4607                              <1> l_dac_p_1:
  4608 00002A88 BE[202E0100]        <1> 	mov	esi, palette1
  4609 00002A8D EB0E                <1> 	jmp	short l_dac_p_4
  4610                              <1> l_dac_p_2:
  4611 00002A8F BE[E02E0100]        <1> 	mov	esi, palette2
  4612 00002A94 EB07                <1> 	jmp	short l_dac_p_4
  4613                              <1> l_dac_p_3:
  4614 00002A96 B4FF                <1> 	mov	ah, 0FFh ; dac registers
  4615 00002A98 BE[A02F0100]        <1> 	mov	esi, palette3
  4616                              <1> l_dac_p_4:
  4617 00002A9D AC                  <1> 	lodsb
  4618 00002A9E EE                  <1> 	out	dx, al  ; Red
  4619 00002A9F AC                  <1> 	lodsb
  4620 00002AA0 EE                  <1> 	out	dx, al	; Green
  4621 00002AA1 AC                  <1> 	lodsb
  4622 00002AA2 EE                  <1> 	out	dx, al	; Blue
  4623 00002AA3 20E4                <1> 	and	ah, ah
  4624 00002AA5 7405                <1> 	jz	short l_dac_p_5	
  4625 00002AA7 FECC                <1> 	dec	ah
  4626 00002AA9 E2F2                <1> 	loop	l_dac_p_4
  4627                              <1> 	;pop	esi
  4628 00002AAB C3                  <1> 	retn
  4629                              <1> l_dac_p_5:
  4630                              <1> 	; 29/07/2016
  4631 00002AAC FEC9                <1> 	dec	cl
  4632 00002AAE 7407                <1> 	jz	short l_dac_p_7
  4633                              <1> 	;
  4634 00002AB0 28C0                <1> 	sub	al, al ; 0
  4635                              <1> l_dac_p_6:
  4636 00002AB2 EE                  <1> 	out	dx, al ; outb(VGAREG_DAC_DATA,0);
  4637 00002AB3 EE                  <1> 	out	dx, al
  4638 00002AB4 EE                  <1> 	out	dx, al
  4639 00002AB5 E2FB                <1> 	loop	l_dac_p_6
  4640                              <1> l_dac_p_7:
  4641                              <1> 	;pop	esi
  4642 00002AB7 C3                  <1> 	retn
  4643                              <1> 
  4644                              <1> gray_scale_summing:
  4645                              <1> 	; 03/07/2016 (TRDOS 386 = TRDOS v2.0)
  4646                              <1> 	; (set_mode_vga)
  4647                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  4648                              <1> 	; vgabios-0.7a (2011)
  4649                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  4650                              <1> 	; 'vgabios.c', 'biosfn_perform_gray_scale_summing'
  4651                              <1> 	;
  4652                              <1> 	; Oracle VirtualBox 5.0.24 VGABios Source Code
  4653                              <1> 	; ('vgabios.c', 'vgatables.h', 'vgafonts.h', 'vgarom.asm')
  4654                              <1> 	;
  4655                              <1> 
  4656                              <1> 	; INPUT -> EBX = Start address (color index <= 255)
  4657                              <1> 	;	   ECX = Count (<= 256)
  4658                              <1> 	; OUTPUT -> (E)CX = 0
  4659                              <1> 	; (Modifed registers: EAX, ECX, EDX, EBX)
  4660                              <1> 
  4661 00002AB8 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  4662 00002ABC EC                  <1> 	in	al, dx
  4663 00002ABD 30C0                <1> 	xor	al, al ; 0
  4664 00002ABF 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  4665 00002AC3 EE                  <1> 	out	dx, al	; clear bit 5
  4666                              <1> 			; (while loading palette registers)
  4667                              <1> 	; set read address and switch to read mode
  4668                              <1> g_s_s_1:
  4669 00002AC4 66BAC703            <1> 	mov	dx, 3C7h ; VGAREG_DAC_READ_ADDRESS
  4670 00002AC8 88D8                <1> 	mov	al, bl
  4671 00002ACA EE                  <1> 	out	dx, al
  4672                              <1> 	; get 6-bit wide RGB data values
  4673                              <1>  	; intensity = (0.3*Red)+(0.59*Green)+(0.11*Blue)
  4674                              <1> 	; i = ( ( 77*r + 151*g + 28*b ) + 0x80 ) >> 8;
  4675 00002ACB 66BAC903            <1> 	mov	dx, 3C9h ; VGAREG_DAC_DATA
  4676 00002ACF EC                  <1> 	in	al, dx ; red
  4677 00002AD0 B44D                <1> 	mov	ah, 77 ; 0.3* Red
  4678 00002AD2 F6E4                <1> 	mul	ah
  4679 00002AD4 6650                <1> 	push	ax
  4680 00002AD6 EC                  <1> 	in	al, dx ; green
  4681 00002AD7 B497                <1> 	mov	ah, 151  ; 0.59 * Green
  4682 00002AD9 F6E4                <1> 	mul	ah
  4683 00002ADB 6650                <1> 	push	ax
  4684 00002ADD EC                  <1> 	in	al, dx ; blue
  4685 00002ADE B41C                <1> 	mov	ah, 28 ; 0.11 * Blue
  4686 00002AE0 F6E4                <1> 	mul	ah
  4687 00002AE2 665A                <1> 	pop	dx
  4688 00002AE4 6601D0              <1> 	add	ax, dx
  4689 00002AE7 665A                <1> 	pop	dx
  4690 00002AE9 6601D0              <1> 	add	ax, dx
  4691 00002AEC 66058000            <1> 	add	ax, 80h  
  4692 00002AF0 B03F                <1> 	mov	al, 3Fh
  4693 00002AF2 38C4                <1> 	cmp	ah, al	; if(i>0x3f)i=0x3f
  4694 00002AF4 7602                <1> 	jna	short g_s_s_2
  4695 00002AF6 88C4                <1> 	mov	ah, al
  4696                              <1> g_s_s_2:
  4697 00002AF8 66BAC803            <1> 	mov	dx, 3C8h  ; VGAREG_DAC_WRITE_ADDRESS
  4698 00002AFC 88D8                <1> 	mov	al, bl ; color index
  4699 00002AFE EE                  <1> 	out	dx, al
  4700 00002AFF 88E0                <1> 	mov	al, ah ; intensity
  4701 00002B01 6642                <1> 	inc	dx ; 3C9h ; VGAREG_DAC_DATA
  4702 00002B03 EE                  <1> 	out	dx, al ; R (R=G=B)
  4703 00002B04 88E0                <1> 	mov	al, ah ; intensity
  4704 00002B06 EE                  <1> 	out	dx, al ; G (R=G=B)
  4705 00002B07 88E0                <1>  	mov	al, ah ; intensity
  4706 00002B09 EE                  <1> 	out	dx, al ; B (R=G=B)
  4707 00002B0A 6649                <1> 	dec	cx
  4708 00002B0C 7404                <1> 	jz	short g_s_s_3
  4709 00002B0E FEC3                <1> 	inc	bl    ; next color index value
  4710 00002B10 EBB2                <1> 	jmp	short g_s_s_1
  4711                              <1> g_s_s_3:
  4712 00002B12 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  4713 00002B16 EC                  <1> 	in	al, dx
  4714 00002B17 B020                <1> 	mov	al, 20h
  4715 00002B19 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  4716 00002B1D EE                  <1> 	out	dx, al ; 20h -> set bit 5
  4717                              <1> 		        ; (after loading palette regs)	
  4718 00002B1E C3                  <1> 	retn
  4719                              <1> 
  4720                              <1> vga_write_char_attr:
  4721                              <1> vga_write_char_only: 
  4722                              <1> 	; 08/07/2016 (TRDOS 386 = TRDOS v2.0)
  4723                              <1> 	;
  4724                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  4725                              <1> 	; vgabios-0.7a (2011)
  4726                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  4727                              <1> 	; 'vgabios.c', 'biosfn_write_char_attr'
  4728                              <1> 	; 'biosfn_write_char_only'
  4729                              <1> 
  4730                              <1> 	; INPUT ->
  4731                              <1> 	; [CRT_MODE] = current video mode (>7)
  4732                              <1> 	; CX = Count of characters to write
  4733                              <1> 	; AL = Character to write
  4734                              <1> 	; BL = Color of character
  4735                              <1> 	; OUTPUT ->
  4736                              <1> 	; Regen buffer updated
  4737                              <1>  
  4738 00002B1F 8A25[7A660000]      <1> 	mov 	ah, [CRT_MODE]
  4739 00002B25 668B15[9E5E0100]    <1> 	mov	dx, [CURSOR_POSN] ; cursor pos for page 0
  4740                              <1> 
  4741 00002B2C BE[96660000]        <1> 	mov	esi, vga_modes
  4742 00002B31 89F7                <1> 	mov	edi, esi
  4743 00002B33 83C710              <1> 	add	edi, vga_mode_count
  4744                              <1> vga_wca_0:
  4745 00002B36 AC                  <1> 	lodsb
  4746 00002B37 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  4747 00002B39 7405                <1> 	je	short vga_wca_2
  4748 00002B3B 39FE                <1> 	cmp	esi, edi
  4749 00002B3D 72F7                <1> 	jb	short vga_wca_0
  4750                              <1> vga_wca_1:
  4751 00002B3F C3                  <1> 	retn	; nothing to do
  4752                              <1> vga_wca_2:
  4753 00002B40 83C64F              <1> 	add	esi, vga_memmodel - (vga_modes + 1)  
  4754                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  4755                              <1> 
  4756                              <1> 	; biosfn_write_char_attr (car,page,attr,count) 
  4757                              <1> 	; AL = car, page = 0, BL = attr, CX = count
  4758 00002B43 803E04              <1> 	cmp	byte [esi], PLANAR4
  4759 00002B46 741D                <1> 	je	short vga_wca_planar
  4760 00002B48 803E03              <1> 	cmp	byte [esi], PLANAR1
  4761 00002B4B 7418                <1> 	je	short vga_wca_planar
  4762                              <1> vga_wca_linear8:
  4763                              <1> 	; while((count-->0) && (xcurs<nbcols))
  4764                              <1> 	; CX = count
  4765 00002B4D 6621C9              <1> 	and	cx, cx
  4766 00002B50 74ED                <1> 	jz	short vga_wca_1
  4767 00002B52 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS]
  4768 00002B58 73E5                <1> 	jnb	short vga_wca_1
  4769                              <1> 	; write_gfx_char_lin(car,attr,xcurs,ycurs,nbcols);
  4770                              <1> 	; AL = car, BL = attr, DL = xcurs, DH = ycurs, 
  4771                              <1> 	; [CRT_COLS] = nbcols
  4772 00002B5A E81E000000          <1> 	call	write_gfx_char_lin	 
  4773 00002B5F 6649                <1> 	dec	cx ; count
  4774 00002B61 FEC2                <1> 	inc	dl ; xcurs
  4775 00002B63 EBE8                <1> 	jmp	short vga_wca_linear8
  4776                              <1> vga_wca_planar:
  4777                              <1> 	; while((count-->0) && (xcurs<nbcols))
  4778                              <1> 	; CX = count
  4779 00002B65 6621C9              <1> 	and	cx, cx
  4780 00002B68 74D5                <1> 	jz	short vga_wca_1
  4781 00002B6A 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS]
  4782 00002B70 73CD                <1> 	jnb	short vga_wca_1
  4783                              <1> 	; write_gfx_char_pl4(car,attr,xcurs,ycurs,nbcols,cheight);
  4784                              <1> 	; AL = car, BL = attr, DL = xcurs, DH = ycurs, 
  4785                              <1> 	; [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight
  4786 00002B72 E89D000000          <1> 	call	write_gfx_char_pl4
  4787 00002B77 6649                <1> 	dec	cx ; count
  4788 00002B79 FEC2                <1> 	inc	dl ; xcurs
  4789 00002B7B EBE8                <1> 	jmp	short vga_wca_planar
  4790                              <1> 
  4791                              <1> write_gfx_char_lin:
  4792                              <1> 	; 08/08/2016
  4793                              <1> 	; 31/07/2016
  4794                              <1> 	; 08/07/2016 (TRDOS 386 = TRDOS v2.0)
  4795                              <1> 	;
  4796                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  4797                              <1> 	; vgabios-0.7a (2011)
  4798                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  4799                              <1> 	; 'vgabios.c', 'write_gfx_char_lin'
  4800                              <1> 
  4801                              <1> 	; write_gfx_char_lin(car,attr,xcurs,ycurs,nbcols)
  4802                              <1> 	; INPUT ->
  4803                              <1> 	; AL = car, BL = attr, DL = xcurs, DH = ycurs, 
  4804                              <1> 	; [CRT_COLS] = nbcols
  4805                              <1> 	; OUTPUT ->
  4806                              <1> 	; Regen buffer updated
  4807                              <1> 
  4808 00002B7D 51                  <1> 	push	ecx
  4809 00002B7E 53                  <1> 	push	ebx
  4810 00002B7F 52                  <1> 	push	edx
  4811 00002B80 50                  <1> 	push	eax
  4812                              <1> 	; addr=xcurs*8+ycurs*nbcols*64;
  4813                              <1> 	; 08/08/2016
  4814 00002B81 0FB6F0              <1> 	movzx	esi, al ; car
  4815 00002B84 0FB6C6              <1> 	movzx	eax, dh ; ycurs
  4816 00002B87 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; nbcols
  4817 00002B8D F6E4                <1> 	mul	ah
  4818                              <1> 	;shl	ax, 6 ; * 64
  4819 00002B8F 66C1E003            <1>  	shl	ax, 3 ; * 8
  4820                              <1> 	;sub	dh, dh
  4821                              <1> 	;shl	dx, 3 ; xcurs * 8
  4822                              <1> 	;movzx	edi, dx
  4823 00002B93 0FB6FA              <1> 	movzx	edi, dl
  4824 00002B96 66C1E703            <1> 	shl	di, 3 ; xcurs * 8
  4825 00002B9A 30F6                <1> 	xor	dh, dh
  4826 00002B9C 8A15[7E660000]      <1> 	mov	dl, [CHAR_HEIGHT]
  4827 00002BA2 66F7E2              <1> 	mul	dx
  4828                              <1> 	; eax = ycurs*nbcols*8*[CHAR_HEIGHT]
  4829 00002BA5 01C7                <1> 	add	edi, eax ; addr
  4830 00002BA7 81C700000A00        <1> 	add	edi, 0A0000h
  4831                              <1> 	;shl	si, 3 ; car * 8
  4832 00002BAD 30E4                <1> 	xor	ah, ah
  4833 00002BAF A0[7E660000]        <1> 	mov	al, [CHAR_HEIGHT]
  4834 00002BB4 66F7E6              <1> 	mul	si
  4835 00002BB7 6689C6              <1> 	mov	si, ax
  4836                              <1> 	;; esi = src = car * 8
  4837                              <1> 	; esi = src = car * [CHAR_HEIGHT]
  4838                              <1> 	; i = 0
  4839                              <1> 	;add	esi, vgafont8 ; fdata [src+i]
  4840                              <1> 	; 08/08/2016
  4841 00002BBA A1[2A6B0100]        <1> 	mov	eax, [VGA_INT43H]
  4842 00002BBF 3D[A0480100]        <1> 	cmp	eax, vgafont16
  4843 00002BC4 740F                <1>         je      short wgfxl_0
  4844 00002BC6 3D[A03A0100]        <1> 	cmp	eax, vgafont14
  4845 00002BCB 7408                <1> 	je	short wgfxl_0
  4846 00002BCD 81C6[A0320100]      <1> 	add	esi, vgafont8
  4847 00002BD3 EB02                <1> 	jmp	short wgfxl_1
  4848                              <1> wgfxl_0:
  4849 00002BD5 01C6                <1> 	add	esi, eax
  4850                              <1> wgfxl_1:
  4851 00002BD7 28FF                <1> 	sub	bh, bh ; i = 0
  4852                              <1> wgfxl_2:
  4853                              <1> 	; for(i=0;i<8;i++)
  4854 00002BD9 57                  <1> 	push	edi ; addr
  4855 00002BDA 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS] ; nbcols
  4856 00002BE1 F6E7                <1> 	mul	bh ; nbcols*i
  4857 00002BE3 66C1E003            <1> 	shl	ax, 3 ; i*nbcols*8
  4858                              <1>  	; dest=addr+i*nbcols*8;
  4859 00002BE7 01C7                <1> 	add	edi, eax ; dest + j ; j = 0
  4860 00002BE9 B180                <1> 	mov	cl, 80h ; mask = 0x80;
  4861                              <1> 	; esi = fdata + src + i
  4862                              <1> 	; for(j=0;j<8;j++)
  4863 00002BEB 29D2                <1> 	sub	edx, edx ; j = 0
  4864                              <1> wgfxl_3:
  4865 00002BED 8A06                <1> 	mov	al, [esi] ; al = fdata[src+i]
  4866 00002BEF 20C8                <1> 	and	al, cl ; if (fdata[src+i] & mask)
  4867 00002BF1 7402                <1> 	jz	short wgfxl_4  ; data = 0, zf = 1
  4868 00002BF3 88D8                <1> 	mov	al, bl ; data = attr;
  4869                              <1> wgfxl_4:
  4870                              <1> 	; write_byte(0xa000,dest+j,data);		
  4871 00002BF5 AA                  <1> 	stosb  ; dest + j (+ 0A0000h)
  4872                              <1> 	;inc	dl ; j++
  4873                              <1> 	;cmp	dl, 8
  4874 00002BF6 80FA07              <1> 	cmp	dl, 7
  4875 00002BF9 720E                <1> 	jb	short wgfxl_5
  4876 00002BFB 5F                  <1> 	pop	edi
  4877                              <1> 	; 08/08/2016
  4878                              <1> 	;cmp	bh, 7
  4879                              <1> 	;jnb	short wgfxl_6
  4880 00002BFC FEC7                <1> 	inc	bh ; i++
  4881 00002BFE 3A3D[7E660000]      <1> 	cmp	bh, [CHAR_HEIGHT]
  4882 00002C04 7309                <1> 	jnb	short wgfxl_6
  4883 00002C06 46                  <1> 	inc	esi
  4884 00002C07 EBD0                <1> 	jmp	short wgfxl_2
  4885                              <1> wgfxl_5:
  4886 00002C09 D0E9                <1> 	shr	cl, 1 ; mask >>= 1;
  4887 00002C0B FEC2                <1> 	inc	dl ; j++
  4888 00002C0D EBDE                <1>         jmp     short wgfxl_3
  4889                              <1> wgfxl_6:
  4890 00002C0F 58                  <1> 	pop	eax
  4891 00002C10 5A                  <1> 	pop	edx
  4892 00002C11 5B                  <1> 	pop	ebx
  4893 00002C12 59                  <1> 	pop	ecx
  4894 00002C13 C3                  <1> 	retn
  4895                              <1> 
  4896                              <1> write_gfx_char_pl4:
  4897                              <1> 	; 08/08/2016
  4898                              <1> 	; 08/07/2016 (TRDOS 386 = TRDOS v2.0)
  4899                              <1> 	;
  4900                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  4901                              <1> 	; vgabios-0.7a (2011)
  4902                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  4903                              <1> 	; 'vgabios.c', 'write_gfx_char_pl4'
  4904                              <1> 
  4905                              <1> 	; write_gfx_char_pl4(car,attr,xcurs,ycurs,nbcols,cheight)
  4906                              <1> 	; INPUT ->
  4907                              <1> 	; AL = car, BL = attr, DL = xcurs, DH = ycurs, 
  4908                              <1> 	; [CRT_COLS] = nbcols, [CHAR_HEIGHT] = cheight
  4909                              <1> 	; OUTPUT ->
  4910                              <1> 	; Regen buffer updated
  4911                              <1> 
  4912 00002C14 51                  <1> 	push	ecx
  4913 00002C15 53                  <1> 	push	ebx
  4914 00002C16 52                  <1> 	push	edx
  4915 00002C17 50                  <1> 	push	eax
  4916                              <1> wgfxpl_f0:
  4917                              <1> 	; switch(cheight)
  4918 00002C18 8A25[7E660000]      <1> 	mov	ah, [CHAR_HEIGHT]
  4919 00002C1E 80FC10              <1> 	cmp	ah, 16 ; case 16:
  4920 00002C21 7507                <1> 	jne	short wgfxpl_f1
  4921                              <1> 	; fdata = &vgafont16;
  4922 00002C23 BE[A0480100]        <1> 	mov	esi, vgafont16
  4923 00002C28 EB13                <1> 	jmp	short wgfxpl_f3
  4924                              <1> wgfxpl_f1:
  4925 00002C2A 80FC0E              <1> 	cmp	ah, 14 ; case 14:
  4926 00002C2D 7507                <1> 	jne	short wgfxpl_f2
  4927 00002C2F BE[A03A0100]        <1> 	mov	esi, vgafont14
  4928 00002C34 EB07                <1> 	jmp	short wgfxpl_f3
  4929                              <1> wgfxpl_f2:
  4930                              <1> 	; default:
  4931                              <1> 	;  fdata = &vgafont8;
  4932 00002C36 BE[A0320100]        <1> 	mov	esi, vgafont8
  4933 00002C3B B408                <1> 	mov	ah, 8	
  4934                              <1> wgfxpl_f3:
  4935                              <1> 	; al = car
  4936 00002C3D F6E4                <1> 	mul	ah ; ah = cheight
  4937 00002C3F 25FFFF0000          <1> 	and	eax, 0FFFFh ; car * cheight
  4938                              <1> 	; src = car * cheight;
  4939 00002C44 01C6                <1> 	add	esi, eax ; esi = fdata[src+i]
  4940                              <1> 	; addr=xcurs*8+ycurs*nbcols*64;
  4941 00002C46 88F0                <1> 	mov	al, dh ; ycurs
  4942 00002C48 8A25[7C660000]      <1> 	mov	ah, [CRT_COLS] ; nbcols
  4943 00002C4E F6E4                <1> 	mul	ah
  4944                              <1> 	; 08/08/2016
  4945                              <1> 	;shl	ax, 6 ; * 64
  4946 00002C50 66C1E003            <1> 	shl	ax, 3 ; * 8
  4947                              <1> 	;sub	dh, dh ; 0
  4948                              <1> 	;shl	dx, 3 ; xcurs * 8
  4949                              <1> 	;movzx	edi, dx
  4950 00002C54 0FB6FA              <1> 	movzx	edi, dl
  4951 00002C57 66C1E703            <1> 	shl	di, 3 ; xcurs * 8
  4952 00002C5B 30F6                <1> 	xor	dh, dh
  4953 00002C5D 8A15[7E660000]      <1> 	mov	dl, [CHAR_HEIGHT]
  4954 00002C63 66F7E2              <1> 	mul	dx
  4955                              <1> 	; eax = ycurs*nbcols*8*[CHAR_HEIGHT]
  4956 00002C66 01C7                <1> 	add	edi, eax ; addr
  4957 00002C68 81C700000A00        <1> 	add	edi, 0A0000h
  4958                              <1> 	;
  4959                              <1> 	; outw(VGAREG_SEQU_ADDRESS, 0x0f02);
  4960                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0205);
  4961 00002C6E 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  4962 00002C72 66B8020F            <1> 	mov	ax, 0F02h
  4963 00002C76 66EF                <1> 	out	dx, ax
  4964 00002C78 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  4965 00002C7C 66B80502            <1> 	mov	ax, 0205h
  4966 00002C80 66EF                <1> 	out	dx, ax
  4967                              <1> 	;
  4968 00002C82 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  4969 00002C86 F6C380              <1> 	test	bl, 80h ; if(attr&0x80)
  4970 00002C89 7406                <1> 	jz	short wgfxpl_f4 ; else
  4971                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x1803);
  4972 00002C8B 66B80318            <1> 	mov	ax, 1803h
  4973 00002C8F EB04                <1> 	jmp	short wgfxpl_f5
  4974                              <1> wgfxpl_f4:
  4975                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0003);
  4976 00002C91 66B80300            <1> 	mov	ax, 0003h	
  4977                              <1> wgfxpl_f5:
  4978 00002C95 66EF                <1> 	out	dx, ax
  4979                              <1> 	;	
  4980 00002C97 28FF                <1> 	sub	bh, bh ; i = 0
  4981                              <1> wgfxpl_0:
  4982                              <1> 	; for(i=0;i<cheight;i++)
  4983 00002C99 57                  <1> 	push	edi ; addr
  4984 00002C9A 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS] ; nbcols
  4985 00002CA1 F6E7                <1> 	mul	bh ; nbcols*i
  4986                              <1> 	; dest=addr+i*nbcols
  4987 00002CA3 01C7                <1> 	add	edi, eax ; dest
  4988 00002CA5 B580                <1> 	mov	ch, 80h ; mask = 0x80;
  4989                              <1> 	; for(j=0;j<8;j++)
  4990 00002CA7 28C9                <1> 	sub	cl, cl ; j = 0
  4991                              <1> wgfxpl_1:
  4992 00002CA9 D2ED                <1> 	shr	ch, cl ; mask=0x80>>j;
  4993                              <1> 	;
  4994                              <1> 	; outw(VGAREG_GRDC_ADDRESS, (mask << 8) | 0x08);
  4995                              <1>      	; read_byte(0xa000,dest);
  4996                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  4997 00002CAB 88EC                <1> 	mov	ah, ch
  4998 00002CAD B008                <1> 	mov	al, 8
  4999 00002CAF 66EF                <1> 	out	dx, ax
  5000 00002CB1 8A07                <1> 	mov	al, [edi] ; ? (io delay?)
  5001                              <1> 	;
  5002 00002CB3 28C0                <1> 	sub	al, al ; attr = 0
  5003                              <1> 	; if (fdata[src+i] & mask)
  5004 00002CB5 842E                <1> 	test	byte [esi], ch
  5005 00002CB7 7404                <1> 	jz	short wgfxpl_2  ; zf = 1
  5006                              <1> 	; write_byte(0xa000,dest,attr&0x0f);
  5007 00002CB9 88D8                <1> 	mov	al, bl ; attr;
  5008 00002CBB 240F                <1> 	and	al, 0Fh	; attr&0x0f
  5009                              <1> wgfxpl_2:
  5010                              <1> 	; write_byte(0xa000,dest,0x00);		
  5011 00002CBD 8807                <1> 	mov	[edi], al ; dest (+ 0A0000h)
  5012 00002CBF FEC1                <1> 	inc	cl ; j++
  5013 00002CC1 80F908              <1> 	cmp	cl, 8
  5014 00002CC4 72E3                <1> 	jb	short wgfxpl_1
  5015 00002CC6 5F                  <1> 	pop	edi
  5016                              <1> 	; 08/08/2016
  5017                              <1> 	;cmp	bh, 7
  5018                              <1> 	;jnb	short wgfxpl_3
  5019 00002CC7 FEC7                <1> 	inc	bh ; i++
  5020 00002CC9 3A3D[7E660000]      <1> 	cmp	bh, [CHAR_HEIGHT]
  5021 00002CCF 7303                <1> 	jnb	short wgfxpl_3
  5022 00002CD1 46                  <1> 	inc	esi
  5023 00002CD2 EBC5                <1> 	jmp	short wgfxpl_0
  5024                              <1> wgfxpl_3:
  5025                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5026 00002CD4 66B808FF            <1>   	mov	ax, 0FF08h
  5027 00002CD8 66EF                <1> 	out	dx, ax
  5028 00002CDA 66B80500            <1> 	mov	ax, 0005h
  5029 00002CDE 66EF                <1> 	out	dx, ax
  5030 00002CE0 66B80300            <1> 	mov	ax, 0003h
  5031 00002CE4 66EF                <1> 	out	dx, ax
  5032                              <1> 	;
  5033 00002CE6 58                  <1> 	pop	eax
  5034 00002CE7 5A                  <1> 	pop	edx
  5035 00002CE8 5B                  <1> 	pop	ebx
  5036 00002CE9 59                  <1> 	pop	ecx
  5037 00002CEA C3                  <1> 	retn
  5038                              <1> 
  5039                              <1> vga_write_pixel: 
  5040                              <1> 	; 09/07/2016 (TRDOS 386 = TRDOS v2.0)
  5041                              <1> 	;
  5042                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5043                              <1> 	; vgabios-0.7a (2011)
  5044                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5045                              <1> 	; 'vgabios.c', 'biosfn_write_pixel'
  5046                              <1> 
  5047                              <1> 	; INPUT ->
  5048                              <1> 	; 	DX = row (0-239)
  5049                              <1> 	; 	CX = column (0-799)
  5050                              <1> 	; 	AL = pixel value
  5051                              <1> 	;	(AH = [CRT_MODE])
  5052                              <1> 	; OUTPUT ->
  5053                              <1> 	; 	none
  5054                              <1>  
  5055 00002CEB 88C3                <1> 	mov	bl, al ; pixel value
  5056                              <1> 	;mov 	ah, [CRT_MODE]
  5057 00002CED BE[96660000]        <1> 	mov	esi, vga_modes
  5058 00002CF2 89F7                <1> 	mov	edi, esi
  5059 00002CF4 83C710              <1> 	add	edi, vga_mode_count
  5060                              <1> vga_wp_0:
  5061 00002CF7 AC                  <1> 	lodsb
  5062 00002CF8 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  5063 00002CFA 7405                <1> 	je	short vga_wp_1
  5064 00002CFC 39FE                <1> 	cmp	esi, edi
  5065 00002CFE 72F7                <1> 	jb	short vga_wp_0
  5066 00002D00 C3                  <1> 	retn	; nothing to do
  5067                              <1> vga_wp_1:
  5068 00002D01 83C64F              <1> 	add	esi, vga_memmodel - (vga_modes + 1)  
  5069                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  5070 00002D04 BF00000A00          <1> 	mov	edi, 0A0000h
  5071                              <1> 	;
  5072 00002D09 803E04              <1> 	cmp	byte [esi], PLANAR4
  5073 00002D0C 741D                <1> 	je	short vga_wp_planar
  5074 00002D0E 803E03              <1> 	cmp	byte [esi], PLANAR1
  5075 00002D11 7418                <1> 	je	short vga_wp_planar
  5076                              <1> vga_wp_linear8:
  5077                              <1> 	; addr=CX+DX*(read_word(BIOSMEM_SEG,BIOSMEM_NB_COLS)*8);
  5078 00002D13 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS] ; = [VGA_COLS] ; nbcols
  5079 00002D1A 66C1E003            <1>      	shl	ax, 3 ; * 8
  5080 00002D1E 66F7E2              <1> 	mul	dx
  5081 00002D21 50                  <1> 	push	eax
  5082                              <1> 	;mov	edi, 0A0000h
  5083 00002D22 6601CF              <1> 	add	di, cx
  5084 00002D25 58                  <1> 	pop	eax
  5085 00002D26 01C7                <1> 	add	edi, eax ; addr
  5086                              <1> 	; write_byte(0xa000,addr,AL);
  5087 00002D28 881F                <1> 	mov	[edi], bl
  5088 00002D2A C3                  <1> 	retn    
  5089                              <1> vga_wp_planar:
  5090                              <1> 	; addr = CX/8+DX*read_word(BIOSMEM_SEG,BIOSMEM_NB_COLS);
  5091 00002D2B 0FB7C1              <1> 	movzx	eax, cx
  5092 00002D2E 66C1E803            <1> 	shr	ax, 3 ; CX/8
  5093 00002D32 50                  <1> 	push	eax
  5094 00002D33 28E4                <1> 	sub	ah, ah ; 0
  5095 00002D35 A0[7C660000]        <1> 	mov	al, [CRT_COLS] ; = [VGA_COLS] ; nbcols
  5096 00002D3A 66F7E2              <1> 	mul	dx
  5097                              <1> 	;mov	edi, 0A0000h
  5098 00002D3D 6601C7              <1>         add     di, ax
  5099 00002D40 58                  <1> 	pop	eax
  5100 00002D41 01C7                <1> 	add	edi, eax ; addr
  5101 00002D43 80E107              <1> 	and	cl, 7
  5102 00002D46 B580                <1> 	mov	ch, 80h ; mask
  5103 00002D48 D2ED                <1> 	shr	ch, cl 	; mask = 0x80 >> (CX & 0x07);
  5104                              <1> 	
  5105                              <1> 	; outw(VGAREG_GRDC_ADDRESS, (mask << 8) | 0x08);
  5106 00002D4A 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5107 00002D4E 88EC                <1> 	mov	ah, ch
  5108 00002D50 B008                <1> 	mov	al, 8
  5109 00002D52 66EF                <1> 	out	dx, ax
  5110                              <1> 	; outw(VGAREG_GRDC_ADDRESS, 0x0205);
  5111 00002D54 66B80502            <1> 	mov	ax, 0205h
  5112 00002D58 66EF                <1> 	out	dx, ax
  5113                              <1> 	; data = read_byte(0xa000,addr);
  5114 00002D5A 8A07                <1> 	mov	al, [edi] ; (delay?)	
  5115                              <1> 	; if (AL & 0x80)
  5116                              <1> 	; {
  5117                              <1> 	;  outw(VGAREG_GRDC_ADDRESS, 0x1803);
  5118                              <1> 	; }
  5119 00002D5C F6C380              <1> 	test	bl, 80h
  5120 00002D5F 7406                <1> 	jz	short vga_wp_2
  5121 00002D61 66B80318            <1> 	mov	ax, 1803h
  5122 00002D65 66EF                <1> 	out	dx, ax
  5123                              <1> vga_wp_2:	
  5124                              <1> 	; write_byte(0xa000,addr,AL);
  5125 00002D67 881F                <1> 	mov	[edi], bl
  5126                              <1> 	;
  5127                              <1> 	;mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5128 00002D69 66B808FF            <1>   	mov	ax, 0FF08h
  5129 00002D6D 66EF                <1> 	out	dx, ax
  5130 00002D6F 66B80500            <1> 	mov	ax, 0005h
  5131 00002D73 66EF                <1> 	out	dx, ax
  5132 00002D75 66B80300            <1> 	mov	ax, 0003h
  5133 00002D79 66EF                <1> 	out	dx, ax
  5134                              <1> 	;
  5135 00002D7B C3                  <1> 	retn
  5136                              <1> 
  5137                              <1> vga_read_pixel: 
  5138                              <1> 	; 09/07/2016 (TRDOS 386 = TRDOS v2.0)
  5139                              <1> 	;
  5140                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5141                              <1> 	; vgabios-0.7a (2011)
  5142                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5143                              <1> 	; 'vgabios.c', 'biosfn_read_pixel'
  5144                              <1> 
  5145                              <1> 	; INPUT ->
  5146                              <1> 	; 	DX = row (0-239)
  5147                              <1> 	; 	CX = column (0-799)
  5148                              <1> 	;	(AH = [CRT_MODE])
  5149                              <1> 	; OUTPUT ->
  5150                              <1> 	; 	AL = pixel value
  5151                              <1> 	 
  5152                              <1> 	;mov 	ah, [CRT_MODE]
  5153 00002D7C BE[96660000]        <1> 	mov	esi, vga_modes
  5154 00002D81 89F7                <1> 	mov	edi, esi
  5155 00002D83 83C710              <1> 	add	edi, vga_mode_count
  5156                              <1> vga_rp_0:
  5157 00002D86 AC                  <1> 	lodsb
  5158 00002D87 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  5159 00002D89 7405                <1> 	je	short vga_rp_1
  5160 00002D8B 39FE                <1> 	cmp	esi, edi
  5161 00002D8D 72F7                <1> 	jb	short vga_rp_0
  5162 00002D8F C3                  <1> 	retn	; nothing to do
  5163                              <1> vga_rp_1:
  5164 00002D90 83C64F              <1> 	add	esi, vga_memmodel - (vga_modes + 1)  
  5165                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  5166 00002D93 BF00000A00          <1> 	mov	edi, 0A0000h
  5167                              <1> 	;
  5168 00002D98 803E04              <1> 	cmp	byte [esi], PLANAR4
  5169 00002D9B 741D                <1> 	je	short vga_rp_planar
  5170 00002D9D 803E03              <1> 	cmp	byte [esi], PLANAR1
  5171 00002DA0 7418                <1> 	je	short vga_rp_planar
  5172                              <1> vga_rp_linear8:
  5173                              <1> 	; addr=CX+DX*(read_word(BIOSMEM_SEG,BIOSMEM_NB_COLS)*8);
  5174 00002DA2 0FB605[7C660000]    <1> 	movzx	eax, byte [CRT_COLS] ; = [VGA_COLS] ; nbcols
  5175 00002DA9 66C1E003            <1>      	shl	ax, 3 ; * 8
  5176 00002DAD 66F7E2              <1> 	mul	dx
  5177 00002DB0 50                  <1> 	push	eax
  5178                              <1> 	;mov	edi, 0A0000h
  5179 00002DB1 6601CF              <1> 	add	di, cx
  5180 00002DB4 58                  <1> 	pop	eax
  5181 00002DB5 01C7                <1> 	add	edi, eax ; addr
  5182                              <1> 	; attr=read_byte(0xa000,addr);
  5183 00002DB7 8A07                <1> 	mov	al, [edi] ; pixel value
  5184 00002DB9 C3                  <1> 	retn    
  5185                              <1> vga_rp_planar:
  5186                              <1> 	; addr = CX/8+DX*read_word(BIOSMEM_SEG,BIOSMEM_NB_COLS);
  5187 00002DBA 0FB7C1              <1> 	movzx	eax, cx
  5188 00002DBD 66C1E803            <1> 	shr	ax, 3 ; CX/8
  5189 00002DC1 50                  <1> 	push	eax
  5190 00002DC2 28E4                <1> 	sub	ah, ah ; 0
  5191 00002DC4 A0[7C660000]        <1> 	mov	al, [CRT_COLS] ; = [VGA_COLS] ; nbcols
  5192 00002DC9 66F7E2              <1> 	mul	dx
  5193                              <1> 	;mov	edi, 0A0000h
  5194 00002DCC 6601C7              <1>         add     di, ax
  5195 00002DCF 58                  <1> 	pop	eax
  5196 00002DD0 01C7                <1> 	add	edi, eax ; addr
  5197 00002DD2 80E107              <1> 	and	cl, 7
  5198 00002DD5 B580                <1> 	mov	ch, 80h ; mask
  5199 00002DD7 D2ED                <1> 	shr	ch, cl 	; mask = 0x80 >> (CX & 0x07);
  5200                              <1> 	; attr = 0x00;
  5201 00002DD9 30DB                <1> 	xor	bl, bl ; attr = bl = 0, 
  5202 00002DDB 30C9                <1> 	xor	cl, cl ; i = cl = 0
  5203                              <1> 	; for(i=0;i<4;i++)
  5204                              <1>       	; {
  5205                              <1>        	;  outw(VGAREG_GRDC_ADDRESS, (i << 8) | 0x04);
  5206                              <1>        	;  data = read_byte(0xa000,addr) & mask;
  5207                              <1>        	;  if (data > 0) attr |= (0x01 << i);
  5208                              <1>       	; }
  5209                              <1> vga_rp_2:
  5210 00002DDD 88CC                <1> 	mov	ah, cl ; i << 8
  5211 00002DDF B004                <1> 	mov	al, 4  ; | 0x04
  5212 00002DE1 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5213 00002DE5 66EF                <1> 	out	dx, ax
  5214                              <1> 	; data = read_byte(0xa000,addr) & mask;
  5215 00002DE7 8A07                <1> 	mov	al, [edi]
  5216 00002DE9 20E8                <1> 	and	al, ch ; & mask
  5217                              <1> 	; if (data > 0) attr |= (0x01 << i);
  5218 00002DEB 08C0                <1> 	or	al, al
  5219 00002DED 7408                <1> 	jz	short vga_rp_3 ; al = 0 
  5220 00002DEF B701                <1> 	mov	bh, 1
  5221 00002DF1 D2E7                <1> 	shl	bh, cl ; (0x01 << i)
  5222 00002DF3 08FB                <1> 	or	bl, bh ; attr |= (0x01 << i)
  5223 00002DF5 88D8                <1> 	mov	al, bl ; pixel value	
  5224                              <1> vga_rp_3:	
  5225 00002DF7 C3                  <1> 	retn
  5226                              <1> 
  5227                              <1> vga_beeper:
  5228                              <1> 	; 04/08/2016  (TRDOS 386 = TRDOS v2.0)
  5229 00002DF8 FB                  <1> 	sti
  5230                              <1> 	;mov	bh, [ACTIVE_PAGE]
  5231 00002DF9 E9C8F3FFFF          <1>         jmp     beeper_gfx
  5232                              <1> 
  5233                              <1> vga_write_teletype:
  5234                              <1> 	; 09/12/2017
  5235                              <1> 	; 06/08/2016
  5236                              <1> 	; 04/08/2016
  5237                              <1> 	; 01/08/2016
  5238                              <1> 	; 31/07/2016
  5239                              <1> 	; 09/07/2016 (TRDOS 386 = TRDOS v2.0)
  5240                              <1> 	;
  5241                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5242                              <1> 	; vgabios-0.7a (2011)
  5243                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5244                              <1> 	; 'vgabios.c', 'biosfn_write_teletype'
  5245                              <1> 	; 'biosfn_write_char_only'
  5246                              <1> 
  5247                              <1> 	; INPUT ->
  5248                              <1> 	; [CRT_MODE] = current video mode (>7)
  5249                              <1> 	; AL = Character to write
  5250                              <1> 	; BL = Color of character
  5251                              <1> 	; OUTPUT ->
  5252                              <1> 	; Regen buffer updated
  5253                              <1> 
  5254                              <1> 	; biosfn_write_teletype (car, page, attr, flag) 
  5255                              <1> 	; car = character (AL)
  5256                              <1> 	; page = 0
  5257                              <1> 	; attr = color (BL)
  5258                              <1> 	; 'flag' not used
  5259                              <1> 
  5260 00002DFE 8A25[7A660000]      <1> 	mov 	ah, [CRT_MODE]
  5261 00002E04 88C7                <1> 	mov	bh, al ; character
  5262 00002E06 668B15[9E5E0100]    <1> 	mov	dx, [CURSOR_POSN] ; cursor pos for page 0
  5263                              <1> 
  5264 00002E0D BE[9E660000]        <1> 	mov	esi, vga_g_modes
  5265 00002E12 89F7                <1> 	mov	edi, esi
  5266 00002E14 83C708              <1> 	add	edi, vga_g_mode_count
  5267                              <1> vga_wtty_0:
  5268 00002E17 AC                  <1> 	lodsb
  5269 00002E18 38E0                <1> 	cmp	al, ah ; [CRT_MODE]
  5270 00002E1A 7405                <1> 	je	short vga_wtty_2
  5271 00002E1C 39FE                <1> 	cmp	esi, edi
  5272 00002E1E 72F7                <1> 	jb	short vga_wtty_0
  5273                              <1> vga_wtty_1:
  5274 00002E20 C3                  <1> 	retn	; nothing to do
  5275                              <1> vga_wtty_2:
  5276 00002E21 80FF07              <1> 	cmp	bh, 07h ; bell (beep)
  5277 00002E24 74D2                <1> 	je	short vga_beeper  ; u11
  5278 00002E26 80FF08              <1> 	cmp	bh, 08h ; backspace
  5279 00002E29 7508                <1> 	jne	short vga_wtty_3
  5280                              <1> 	; if(xcurs>0)xcurs--;
  5281 00002E2B 08D2                <1> 	or	dl, dl ; xcurs (column)
  5282 00002E2D 74F1                <1> 	jz	short vga_wtty_1
  5283 00002E2F FECA                <1> 	dec	dl ; xcurs--;
  5284 00002E31 EB59                <1>         jmp     short vga_wtty_12 
  5285                              <1> vga_wtty_3:			
  5286 00002E33 80FF0D              <1> 	cmp	bh, 0Dh ; carriage return (\r)
  5287 00002E36 7504                <1> 	jne	short vga_wtty_4
  5288                              <1> 	; xcurs=0;
  5289 00002E38 28D2                <1> 	sub	dl, dl ; 0
  5290 00002E3A EB50                <1>         jmp     short vga_wtty_12 
  5291                              <1> vga_wtty_4:	
  5292 00002E3C 80FF0A              <1> 	cmp	bh, 0Ah ; new line (\n)
  5293 00002E3F 7504                <1> 	jne	short vga_wtty_5
  5294                              <1> 	; ycurs++;
  5295 00002E41 FEC6                <1> 	inc	dh ; next row
  5296 00002E43 EB62                <1>         jmp     short vga_wtty_11
  5297                              <1> vga_wtty_5:
  5298 00002E45 80FF09              <1> 	cmp 	bh, 09h ; tab stop
  5299 00002E48 7527                <1> 	jne	short vga_wtty_8
  5300 00002E4A 88D0                <1> 	mov	al, dl
  5301                              <1> 	;cbw
  5302 00002E4C 30E4                <1> 	xor	ah, ah ; 09/12/2017
  5303 00002E4E B108                <1> 	mov	cl, 8
  5304 00002E50 F6F1                <1> 	div	cl
  5305 00002E52 28E1                <1> 	sub	cl, ah
  5306                              <1> 	;
  5307 00002E54 B720                <1> 	mov	bh, 20h ; space
  5308                              <1> vga_wtty_6: ; tab stop loop
  5309 00002E56 6651                <1> 	push	cx
  5310 00002E58 6653                <1> 	push	bx
  5311 00002E5A E812000000          <1> 	call	vga_wtty_8
  5312 00002E5F 665B                <1> 	pop	bx  ; bh = character, bl = color
  5313 00002E61 6659                <1> 	pop	cx
  5314 00002E63 FEC9                <1> 	dec	cl
  5315 00002E65 7409                <1> 	jz	short vga_wtty_7
  5316 00002E67 668B15[9E5E0100]    <1> 	mov	dx, [CURSOR_POSN] ; new cursor position (pg 0)
  5317 00002E6E EBE6                <1> 	jmp	short vga_wtty_6
  5318                              <1> vga_wtty_7:
  5319 00002E70 C3                  <1> 	retn
  5320                              <1> 	;
  5321                              <1> vga_wtty_8:
  5322 00002E71 83C64F              <1> 	add	esi, vga_g_memmodel - (vga_g_modes + 1)  
  5323                              <1> 	; [ESI] = VGA memory model number (LINEAR8, PLANAR4, PLANAR1)
  5324 00002E74 BF00000A00          <1> 	mov	edi, 0A0000h
  5325                              <1> 	;
  5326 00002E79 88F8                <1> 	mov	al, bh ; character
  5327                              <1> 	;
  5328 00002E7B 803E04              <1> 	cmp	byte [esi], PLANAR4
  5329 00002E7E 7414                <1> 	je	short vga_wtty_planar
  5330 00002E80 803E03              <1> 	cmp	byte [esi], PLANAR1
  5331 00002E83 740F                <1> 	je	short vga_wtty_planar
  5332                              <1> vga_wtty_linear8:
  5333                              <1> 	; write_gfx_char_lin(car,attr,xcurs,ycurs,nbcols);
  5334                              <1> 	; AL = car, BL = attr (color), DL = xcurs, DH = ycurs, 
  5335                              <1> 	; [CRT_COLS] = nbcols
  5336 00002E85 E8F3FCFFFF          <1> 	call	write_gfx_char_lin
  5337 00002E8A EB0D                <1> 	jmp	short vga_wtty_9
  5338                              <1> 
  5339                              <1> vga_wtty_12:
  5340                              <1> 	; 09/07/2016
  5341                              <1> 	; set cursor position
  5342                              <1> 	; NOTE: Hardware cursor position will not be set
  5343                              <1> 	;   in any VGA modes (>7)
  5344                              <1> 	;   But, cursor position will be saved into
  5345                              <1> 	;   [CURSOR_POSN].
  5346                              <1> 	;   TRDOS 386 (TRDOS v2.0) uses only one page
  5347                              <1> 	;   (page 0) for all graphics modes.
  5348                              <1> 
  5349 00002E8C 668915[9E5E0100]    <1> 	mov	[CURSOR_POSN], dx ; save cursor pos for pg 0
  5350                              <1> 	; 04/08/2016
  5351                              <1> 	;mov	bh, [ACTIVE_PAGE] ; = 0
  5352                              <1> 	;call	_set_cpos
  5353 00002E93 C3                  <1> 	retn
  5354                              <1> 
  5355                              <1> vga_wtty_planar:
  5356                              <1> 	; write_gfx_char_pl4(car,attr,xcurs,ycurs,nbcols,cheight);
  5357                              <1> 	; AL = car, BL = attr (color), DL = xcurs, DH = ycurs, 
  5358                              <1> 	; [CRT_COLS]= nbcols, [CHAR_HEIGHT] = cheight
  5359 00002E94 E87BFDFFFF          <1> 	call	write_gfx_char_pl4
  5360                              <1> vga_wtty_9:
  5361 00002E99 FEC2                <1> 	inc	dl ; xcurs++;
  5362                              <1> vga_wtty_10:
  5363                              <1> 	; Do we need to wrap ?
  5364                              <1> 	; if(xcurs==nbcols)
  5365 00002E9B 3A15[7C660000]      <1> 	cmp	dl, [CRT_COLS] ; [VGA_COLS]
  5366 00002EA1 7204                <1> 	jb	short vga_wtty_11 ; no
  5367 00002EA3 28D2                <1> 	sub	dl, dl ; xcurs=0;
  5368 00002EA5 FEC6                <1> 	inc	dh ;  ycurs++;
  5369                              <1> vga_wtty_11:
  5370                              <1> 	; Do we need to scroll ?
  5371                              <1> 	; if(ycurs==nbrows)
  5372 00002EA7 3A35[82660000]      <1> 	cmp	dh, [VGA_ROWS]
  5373 00002EAD 72DD                <1> 	jb	short vga_wtty_12 ; no
  5374                              <1> 	;
  5375                              <1> 	; biosfn_scroll (nblines,attr,rul,cul,rlr,clr,page,dir)
  5376                              <1> 	; al = nblines = 1, bl = attr (color) = 0
  5377                              <1> 	; ch = rul, cl = cul, dh = rlr, dl = clr, page = 0
  5378                              <1> 	; dir = SCROLL_UP
  5379                              <1> 	
  5380 00002EAF B001                <1> 	mov	al, 1
  5381 00002EB1 28DB                <1> 	sub	bl, bl ; 0 ; blank/black line (attr=0) will be used
  5382 00002EB3 6629C9              <1> 	sub	cx, cx ; 0,0
  5383                              <1> 
  5384                              <1> 	; 06/08/2016
  5385 00002EB6 8A35[82660000]      <1> 	mov	dh, [VGA_ROWS]
  5386 00002EBC FECE                <1> 	dec	dh ; nbrows -1
  5387                              <1> 
  5388 00002EBE 6652                <1> 	push	dx 	; 04/08/2016
  5389 00002EC0 8A15[7C660000]      <1> 	mov	dl, [CRT_COLS]
  5390 00002EC6 FECA                <1> 	dec	dl ; nbcols -1
  5391                              <1> 	
  5392 00002EC8 8A25[7A660000]      <1> 	mov	ah, [CRT_MODE]
  5393                              <1> 	
  5394                              <1> 	; biosfn_scroll(0x01,0x00,0,0,nbrows-1,nbcols-1,page,SCROLL_UP);
  5395 00002ECE E807F5FFFF          <1> 	call	vga_graphics_up
  5396                              <1> 	; 04/08/2016
  5397 00002ED3 665A                <1> 	pop	dx
  5398                              <1> 	;dec	dh ; ycurs-=1
  5399 00002ED5 EBB5                <1> 	jmp	short vga_wtty_12 
  5400                              <1> 
  5401                              <1> font_setup:
  5402                              <1> 	; 09/07/2016
  5403                              <1> 	; character generator (font loading) functions
  5404                              <1> 	;
  5405                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5406                              <1> 	; vgabios-0.7a (2011)
  5407                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5408                              <1> 	; 'vgabios.c', 'int10_func'
  5409                              <1> 
  5410                              <1> 	; AX = 1100H ; Load User-Defined Font (EGA/VGA)
  5411                              <1> 	;
  5412                              <1>         ; BH    height of each character (bytes per character definition)
  5413                              <1>         ; (BL   font block to load (EGA: 0-3; VGA: 0-7))
  5414                              <1> 	; CX    number of characters to redefine (<=256)
  5415                              <1>         ; DX    ASCII code of the first character defined at ES:BP
  5416                              <1>         ; EBP	address of font-definition information
  5417                              <1> 	;	(in user's memory space)
  5418                              <1> 
  5419                              <1> 	; case 0x11:
  5420                              <1>      	; switch(GET_AL())
  5421                              <1>       	; {
  5422                              <1> 	; case 0x00:
  5423                              <1>         ; case 0x10:
  5424                              <1>         ; biosfn_load_text_user_pat(GET_AL(),ES,BP,CX,DX,GET_BL(),GET_BH());
  5425                              <1>         ; break;
  5426                              <1> 
  5427                              <1> 	; AX = 1110H ; Load and Activate User-Defined Font (EGA/VGA)
  5428 00002ED7 08C0                <1> 	or	al, al ; 0
  5429 00002ED9 7404                <1> 	jz	short font_setup_0
  5430 00002EDB 3C10                <1> 	cmp	al, 10h
  5431 00002EDD 7511                <1> 	jne	short font_setup_1	
  5432                              <1> font_setup_0:
  5433 00002EDF E8B7000000          <1> 	call	transfer_user_fonts
  5434 00002EE4 721C                <1> 	jc	short font_setup_error
  5435 00002EE6 E8C2000000          <1> 	call	load_text_user_pat
  5436 00002EEB E966EAFFFF          <1>         jmp     VIDEO_RETURN 
  5437                              <1> font_setup_1:
  5438                              <1> 	; AX = 1101H ; Load ROM 8x14 Character Set (EGA/VGA)
  5439                              <1> 	; case 0x01:
  5440                              <1>         ; case 0x11:
  5441                              <1>         ; biosfn_load_text_8_14_pat(GET_AL(),GET_BL());
  5442                              <1>         ; break;
  5443 00002EF0 3C01                <1> 	cmp	al, 1
  5444 00002EF2 7404                <1> 	je	short font_setup_2
  5445 00002EF4 3C11                <1> 	cmp	al, 11h
  5446 00002EF6 7511                <1> 	jne	short font_setup_3	
  5447                              <1> font_setup_2:
  5448                              <1> 	; AX = 1111H ; Load and Activate ROM 8x14 Character Set (EGA/VGA)
  5449                              <1> 	; (BL = font block to load (EGA: 0-3; VGA: 0-7))
  5450 00002EF8 E8EC010000          <1> 	call	load_text_8_14_pat
  5451 00002EFD E954EAFFFF          <1>         jmp     VIDEO_RETURN
  5452                              <1> font_setup_error:
  5453 00002F02 29C0                <1> 	sub	eax, eax ; 0 -> fonts could not be loaded
  5454 00002F04 E952EAFFFF          <1> 	jmp	_video_return
  5455                              <1> font_setup_3:
  5456                              <1> 	; AX = 1102H ; Load ROM 8x8 Character Set (EGA/VGA)
  5457                              <1> 	; case 0x02:
  5458                              <1>         ; case 0x12:
  5459                              <1>         ; biosfn_load_text_8_8_pat(GET_AL(),GET_BL());
  5460                              <1>         ; break;
  5461 00002F09 3C02                <1> 	cmp	al, 2
  5462 00002F0B 7404                <1> 	je	short font_setup_4
  5463 00002F0D 3C12                <1> 	cmp	al, 12h
  5464 00002F0F 750A                <1> 	jne	short font_setup_5	
  5465                              <1> font_setup_4:
  5466                              <1> 	; AX = 1112H ; Load and Activate ROM 8x8 Character Set (EGA/VGA)
  5467                              <1> 	; (BL = font block to load (EGA: 0-3; VGA: 0-7))
  5468 00002F11 E803020000          <1> 	call	load_text_8_8_pat
  5469 00002F16 E93BEAFFFF          <1>         jmp     VIDEO_RETURN
  5470                              <1> font_setup_5:
  5471                              <1> 	; AX = 1104H ; Load ROM 8x16 Character Set (EGA/VGA)
  5472                              <1> 	; case 0x04:
  5473                              <1>         ; case 0x14:
  5474                              <1>         ; biosfn_load_text_8_16_pat(GET_AL(),GET_BL());
  5475                              <1>         ; break;
  5476 00002F1B 3C04                <1> 	cmp	al, 4
  5477 00002F1D 7404                <1> 	je	short font_setup_6
  5478 00002F1F 3C14                <1> 	cmp	al, 14h
  5479 00002F21 750A                <1> 	jne	short font_setup_7	
  5480                              <1> font_setup_6:
  5481                              <1> 	; AX = 1114H ; Load and Activate ROM 8x16 Character Set (EGA/VGA)
  5482                              <1> 	; (BL = font block to load (EGA: 0-3; VGA: 0-7))
  5483 00002F23 E821020000          <1> 	call	load_text_8_16_pat
  5484 00002F28 E929EAFFFF          <1>         jmp     VIDEO_RETURN
  5485                              <1> font_setup_7:
  5486                              <1> 	; Note: AX=1120h (Setup INT 1Fh, EXT_PTR) is not needed
  5487                              <1> 	; for TRDOS 386 (TRDIOS v2.0) video functionality;
  5488                              <1> 	; because, originally EXT_PTR (font address) was used for
  5489                              <1> 	; chars 80h to 0FFh (after the first 128 ASCII char fonts), for
  5490                              <1> 	; CGA graphics mode; currenty, 'vgafont8' address has 256 chars!
  5491                              <1> 	; 
  5492                              <1> 	; case 0x20:
  5493                              <1>         ; biosfn_load_gfx_8_8_chars(ES,BP);
  5494                              <1>         ; break; 
  5495                              <1> 	; case 0x21:
  5496                              <1>         ; biosfn_load_gfx_user_chars(ES,BP,CX,GET_BL(),GET_DL());
  5497                              <1>         ; break;
  5498                              <1> 	; AX = 1121H ; Setup User-Defined Font for Graphics Mode (VGA)
  5499                              <1> 	; BL   screen rows code: 00H = user-specified (in DL)
  5500                              <1>         ;                        01H = 14 rows
  5501                              <1>         ;                        02H = 25 rows
  5502                              <1>         ;                        03H = 43 rows
  5503                              <1>         ; CX   bytes per character definition
  5504                              <1>         ; DL   (when BL=0) custom number of character rows on screen
  5505                              <1>         ; EBP  address of font-definition information (user's mem space)
  5506                              <1> 
  5507 00002F2D 3C21                <1> 	cmp	al, 21h
  5508 00002F2F 751A                <1> 	jne	short font_setup_9
  5509                              <1> 
  5510                              <1> 	; TRDOS 386 modification !
  5511                              <1> 	; dh = 0 -> 256 characters
  5512                              <1> 	; dh = 80h -> 128 characters
  5513                              <1> 	; (If DH <> 0 and DH <> 80h -> invalid)     
  5514 00002F31 20F6                <1> 	and	dh, dh
  5515 00002F33 7405                <1> 	jz	short font_setup_8 ; 256 characters
  5516 00002F35 80FE80              <1> 	cmp	dh, 80h ; 128 characters
  5517 00002F38 75C8                <1> 	jne	short font_setup_error ; invalid !
  5518                              <1> font_setup_8:
  5519 00002F3A E85C000000          <1> 	call	transfer_user_fonts
  5520 00002F3F 72C1                <1> 	jc	short font_setup_error
  5521                              <1> 	; ebp = user's font data address in system's memory space
  5522 00002F41 E834020000          <1> 	call	load_gfx_user_chars
  5523 00002F46 E90BEAFFFF          <1>         jmp     VIDEO_RETURN 
  5524                              <1> font_setup_9:
  5525                              <1> 	; case 0x22:
  5526                              <1>         ; biosfn_load_gfx_8_14_chars(GET_BL());
  5527                              <1>         ; break;
  5528 00002F4B 3C22                <1> 	cmp	al, 22h
  5529 00002F4D 750A                <1> 	jne	short font_setup_10
  5530 00002F4F E864020000          <1> 	call	load_gfx_8_14_chars	
  5531 00002F54 E9FDE9FFFF          <1>         jmp     VIDEO_RETURN 
  5532                              <1> font_setup_10:	
  5533                              <1> 	; case 0x23:
  5534                              <1>         ; biosfn_load_gfx_8_8_dd_chars(GET_BL());
  5535                              <1>         ; break;
  5536 00002F59 3C23                <1> 	cmp	al, 23h
  5537 00002F5B 750A                <1> 	jne	short font_setup_11
  5538 00002F5D E897020000          <1> 	call	load_gfx_8_8_chars	
  5539 00002F62 E9EFE9FFFF          <1>         jmp     VIDEO_RETURN 
  5540                              <1> font_setup_11:	
  5541                              <1> 	; case 0x24:
  5542                              <1>         ; biosfn_load_gfx_8_16_chars(GET_BL());
  5543                              <1>         ; break;
  5544 00002F67 3C24                <1> 	cmp	al, 24h
  5545 00002F69 750A                <1> 	jne	short font_setup_12
  5546 00002F6B E8CA020000          <1> 	call	load_gfx_8_16_chars	
  5547 00002F70 E9E1E9FFFF          <1>         jmp     VIDEO_RETURN 
  5548                              <1> font_setup_12:
  5549                              <1>  	; case 0x30:
  5550                              <1>         ; biosfn_get_font_info(GET_BH(),&ES,&BP,&CX,&DX);
  5551                              <1>         ; break;
  5552 00002F75 3C30                <1> 	cmp	al, 30h
  5553 00002F77 750A                <1> 	jne	short font_setup_13			
  5554 00002F79 E8FD020000          <1> 	call	get_font_info
  5555                              <1> 	; eax = return value (info: 4 bytes for 4 parms)
  5556                              <1> 	; eax = 0 -> invalid function (input)
  5557 00002F7E E9D8E9FFFF          <1>         jmp     _video_return
  5558                              <1> font_setup_13:
  5559 00002F83 3C03                <1> 	cmp	al, 03h ; AX = 1103h	
  5560 00002F85 750D                <1> 	jne	short font_setup_14
  5561                              <1> 	; biosfn_set_text_block_specifier:
  5562                              <1> 	; BL = font block selector code	
  5563                              <1> 	; NOTE: TRDOS 386 only uses and sets font block 0
  5564                              <1> 	; (It is as BL = 0 for TRDOS 386)
  5565 00002F87 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  5566                              <1> 	;mov	ah, bl
  5567 00002F8B 28E4                <1> 	sub	ah, ah ; 0
  5568                              <1> 	;mov	al, 03h
  5569 00002F8D 66EF                <1> 	out	dx, ax
  5570 00002F8F E9C2E9FFFF          <1> 	jmp     VIDEO_RETURN 
  5571                              <1> 	
  5572                              <1> font_setup_14:
  5573 00002F94 29C0                <1> 	sub	eax, eax ; 0 = invalid function
  5574 00002F96 E9C0E9FFFF          <1>         jmp     _video_return
  5575                              <1> 
  5576                              <1> transfer_user_fonts:
  5577                              <1> 	; 09/07/2016
  5578                              <1> 	;and	ecx, 0FFFFh
  5579                              <1> 	; ECX = byte count
  5580                              <1> 	;push	ecx
  5581 00002F9B 89EE                <1> 	mov	esi, ebp ; user buffer
  5582 00002F9D BF00000700          <1> 	mov	edi, Cluster_Buffer  ; system buffer
  5583 00002FA2 E805BE0000          <1> 	call	transfer_from_user_buffer
  5584                              <1> 	;pop	ecx
  5585                              <1> 	; ecx = transfer (byte) count = character count
  5586 00002FA7 BD00000700          <1> 	mov	ebp, Cluster_Buffer
  5587                              <1> 	; jc	VIDEO_RETURN -> failed
  5588 00002FAC C3                  <1> 	retn
  5589                              <1> 
  5590                              <1> load_text_user_pat:
  5591                              <1> 	; 26/07/2016
  5592                              <1> 	; 09/07/2016
  5593                              <1> 	; load user defined (EGA/VGA) text fonts
  5594                              <1> 	;
  5595                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5596                              <1> 	; vgabios-0.7a (2011)
  5597                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5598                              <1> 	; 'vgabios.c', 'biosfn_load_text_user_pat'
  5599                              <1> 
  5600                              <1> 	; biosfn_load_text_user_pat (AL,ES,BP,CX,DX,BL,BH)
  5601                              <1> 
  5602                              <1> 	; get_font_access();
  5603                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5604                              <1> 	; for(i=0;i<CX;i++)
  5605                              <1> 	; {
  5606                              <1> 	;  src = BP + i * BH;
  5607                              <1> 	;  dest = blockaddr + (DX + i) * 32;
  5608                              <1> 	;  memcpyb(0xA000, dest, ES, src, BH);
  5609                              <1> 	; }
  5610                              <1> 	; release_font_access();
  5611                              <1> 	; if(AL>=0x10)
  5612                              <1> 	; {
  5613                              <1> 	; set_scan_lines(BH);
  5614                              <1> 	; }
  5615                              <1> 
  5616 00002FAD 50                  <1> 	push	eax
  5617 00002FAE E83C000000          <1> 	call	get_font_access
  5618 00002FB3 28DB                <1> 	sub	bl, bl ; i = 0	
  5619                              <1> ltup_1:
  5620 00002FB5 88D8                <1> 	mov	al, bl
  5621 00002FB7 F6E7                <1> 	mul	bh
  5622 00002FB9 0FB7F0              <1> 	movzx	esi, ax
  5623 00002FBC 01EE                <1> 	add	esi, ebp
  5624 00002FBE 88D8                <1> 	mov	al, bl
  5625 00002FC0 28E4                <1> 	sub	ah, ah
  5626 00002FC2 6601D0              <1> 	add	ax, dx ; (DX + i)
  5627 00002FC5 66C1E005            <1> 	shl	ax, 5  ; * 32
  5628 00002FC9 0FB7F8              <1> 	movzx	edi, ax
  5629 00002FCC 81C700000A00        <1> 	add	edi, 0A0000h
  5630 00002FD2 51                  <1> 	push	ecx
  5631 00002FD3 0FB6CF              <1> 	movzx	ecx, bh 		
  5632 00002FD6 F3A4                <1> 	rep	movsb
  5633 00002FD8 59                  <1> 	pop	ecx	
  5634 00002FD9 FEC3                <1> 	inc	bl
  5635 00002FDB 38CB                <1> 	cmp	bl, cl
  5636 00002FDD 75D6                <1> 	jne	short ltup_1	
  5637                              <1> 	;
  5638 00002FDF E840000000          <1> 	call	release_font_access
  5639                              <1> 	;
  5640 00002FE4 58                  <1> 	pop	eax
  5641                              <1> 	; if(AL>=0x10)
  5642 00002FE5 3C10                <1> 	cmp	al, 10h
  5643 00002FE7 7205                <1> 	jb	short ltup_2
  5644                              <1>    	; set_scan_lines(BH);
  5645 00002FE9 E875000000          <1> 	call	set_scan_lines
  5646                              <1> ltup_2:
  5647 00002FEE C3                  <1> 	retn
  5648                              <1> 
  5649                              <1> get_font_access:
  5650                              <1> 	; 09/07/2016
  5651                              <1> 	;
  5652                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5653                              <1> 	; vgabios-0.7a (2011)
  5654                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5655                              <1> 	; 'vgabios.c', 'get_font_access'
  5656                              <1> 
  5657                              <1> 	; get_font_access()
  5658 00002FEF 52                  <1> 	push	edx
  5659 00002FF0 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  5660 00002FF4 66B80001            <1> 	mov	ax, 0100h
  5661 00002FF8 66EF                <1> 	out	dx, ax
  5662 00002FFA 66B80204            <1> 	mov	ax, 0402h
  5663 00002FFE 66EF                <1> 	out	dx, ax
  5664 00003000 66B80407            <1> 	mov	ax, 0704h
  5665 00003004 66EF                <1> 	out	dx, ax
  5666 00003006 66B80003            <1> 	mov	ax, 0300h
  5667 0000300A 66EF                <1> 	out	dx, ax
  5668 0000300C 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5669 00003010 66B80402            <1> 	mov	ax, 0204h
  5670 00003014 66EF                <1> 	out	dx, ax
  5671 00003016 66B80500            <1> 	mov	ax, 0005h
  5672 0000301A 66EF                <1> 	out	dx, ax
  5673 0000301C 66B80604            <1> 	mov	ax, 0406h
  5674 00003020 66EF                <1> 	out	dx, ax
  5675 00003022 5A                  <1> 	pop	edx
  5676 00003023 C3                  <1> 	retn
  5677                              <1> 
  5678                              <1> release_font_access:
  5679                              <1> 	; 29/07/2016
  5680                              <1> 	; 09/07/2016
  5681                              <1> 	;
  5682                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5683                              <1> 	; vgabios-0.7a (2011)
  5684                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5685                              <1> 	; 'vgabios.c', 'release_font_access'
  5686                              <1> 
  5687 00003024 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  5688 00003028 66B80001            <1> 	mov	ax, 0100h
  5689 0000302C 66EF                <1> 	out	dx, ax
  5690 0000302E 66B80203            <1> 	mov	ax, 0302h
  5691 00003032 66EF                <1> 	out	dx, ax
  5692 00003034 66B80403            <1> 	mov	ax, 0304h
  5693 00003038 66EF                <1> 	out	dx, ax
  5694 0000303A 66B80003            <1> 	mov	ax, 0300h
  5695 0000303E 66EF                <1> 	out	dx, ax
  5696 00003040 66BACC03            <1> 	mov	dx, 3CCh ; VGAREG_READ_MISC_OUTPUT
  5697 00003044 EC                  <1>  	in	al, dx
  5698 00003045 2401                <1> 	and	al, 01h
  5699 00003047 C0E002              <1> 	shl	al, 2
  5700 0000304A 0C0A                <1> 	or	al, 0Ah
  5701 0000304C 88C4                <1> 	mov	ah, al
  5702 0000304E B006                <1> 	mov	al, 06h
  5703 00003050 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  5704 00003054 66EF                <1> 	out	dx, ax
  5705 00003056 66B80400            <1> 	mov	ax, 0004h
  5706 0000305A 66EF                <1> 	out	dx, ax
  5707 0000305C 66B80510            <1> 	mov	ax, 1005h
  5708 00003060 66EF                <1> 	out	dx, ax
  5709 00003062 C3                  <1> 	retn
  5710                              <1> 
  5711                              <1> set_scan_lines:
  5712                              <1> 	; 09/07/2016
  5713                              <1> 	;
  5714                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5715                              <1> 	; vgabios-0.7a (2011)
  5716                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5717                              <1> 	; 'vgabios.c', 'set_scan_lines'
  5718                              <1> 
  5719                              <1> 	; set_scan_lines(lines)
  5720                              <1> 	; BH = lines
  5721                              <1> 
  5722                              <1> 	; outb(crtc_addr, 0x09);
  5723 00003063 66BAD403            <1> 	mov	dx, 3D4h ; CRTC_ADDRESS = 3D4h (always)
  5724 00003067 B009                <1> 	mov	al, 09h
  5725 00003069 EE                  <1> 	out	dx, al
  5726                              <1> 	; crtc_r9 = inb(crtc_addr+1);
  5727 0000306A 6642                <1> 	inc	dx ; 3D5h
  5728 0000306C EC                  <1> 	in	al, dx
  5729                              <1> 	; crtc_r9 = (crtc_r9 & 0xe0) | (lines - 1);
  5730 0000306D 24E0                <1> 	and	al, 0E0h
  5731 0000306F FECF                <1> 	dec	bh ; lines - 1
  5732 00003071 08F8                <1> 	or	al, bh
  5733                              <1> 	; outb(crtc_addr+1, crtc_r9);
  5734 00003073 EE                  <1> 	out	dx, al
  5735                              <1> 	;inc	bh 
  5736                              <1> 	; if(lines==8)
  5737                              <1> 	;cmp	bh, 8
  5738 00003074 80FF07              <1> 	cmp	bh, 7
  5739 00003077 7506                <1> 	jne	short ssl_1
  5740                              <1> 	; biosfn_set_cursor_shape(0x06,0x07);
  5741 00003079 66B90706            <1> 	mov	cx, 0607h
  5742 0000307D EB06                <1> 	jmp	short ssl_2
  5743                              <1> ssl_1:
  5744                              <1> 	; biosfn_set_cursor_shape(lines-4,lines-3);
  5745 0000307F 88F9                <1> 	mov	cl, bh ; lines - 1
  5746 00003081 88CD                <1> 	mov	ch, cl ; lines - 1 (16 -> 15)
  5747 00003083 FECD                <1> 	dec	ch  ; lines - 2 (16 -> 14)
  5748                              <1> ssl_2:
  5749                              <1> 	; CH = start line, CL = stop line
  5750 00003085 B40A                <1> 	mov	ah, 10	; 6845 register for cursor set
  5751 00003087 66890D[93660000]    <1> 	mov	[CURSOR_MODE], cx ; save in data area
  5752 0000308E E80BF1FFFF          <1> 	call	m16	; output cx register
  5753                              <1> 	; write_word(BIOSMEM_SEG,BIOSMEM_CHAR_HEIGHT, lines);
  5754 00003093 FEC7                <1> 	inc	bh ; lines
  5755 00003095 883D[7E660000]      <1> 	mov	[CHAR_HEIGHT], bh
  5756                              <1> 	;  outb(crtc_addr, 0x12);
  5757 0000309B 66BAD403            <1> 	mov	dx, 3D4h ; CRTC_ADDRESS
  5758 0000309F B012                <1> 	mov	al, 12h
  5759 000030A1 EE                  <1> 	out	dx, al
  5760                              <1> 	; vde = inb(crtc_addr+1);
  5761 000030A2 6642                <1> 	inc	dx
  5762 000030A4 EC                  <1> 	in	al, dx
  5763 000030A5 88C4                <1> 	mov	ah, al
  5764                              <1> 	; outb(crtc_addr, 0x07);
  5765 000030A7 664A                <1> 	dec	dx
  5766 000030A9 B007                <1> 	mov	al, 07h
  5767 000030AB EE                  <1> 	out	dx, al
  5768                              <1> 	; ovl = inb(crtc_addr+1);
  5769 000030AC 6642                <1> 	inc	dx
  5770 000030AE EC                  <1> 	in	al, dx
  5771                              <1> 	; vde += (((ovl & 0x02) << 7) + ((ovl & 0x40) << 3) + 1);
  5772 000030AF 88E2                <1> 	mov	dl, ah ; vde
  5773 000030B1 88C6                <1> 	mov	dh, al ; ovl
  5774 000030B3 6683E002            <1> 	and	ax, 02h
  5775 000030B7 66C1E007            <1> 	shl	ax, 7
  5776 000030BB 6689C1              <1> 	mov	cx, ax ; (ovl & 0x02) << 7)	
  5777 000030BE 88F0                <1> 	mov	al, dh ; ovl
  5778 000030C0 6683E040            <1> 	and	ax, 40h			
  5779 000030C4 66C1E003            <1> 	shl	ax, 3  ; (ovl & 0x40) << 3)
  5780 000030C8 6640                <1> 	inc	ax ; + 1 
  5781 000030CA 6601C8              <1> 	add	ax, cx
  5782 000030CD 30F6                <1> 	xor	dh, dh
  5783 000030CF 6601D0              <1> 	add	ax, dx ; + vde
  5784                              <1> 	; rows = vde / lines;
  5785 000030D2 F6F7                <1> 	div	bh
  5786                              <1> 	;dec	al ; rows -1
  5787                              <1> 	; write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, rows-1);
  5788 000030D4 A2[82660000]        <1> 	mov	[VGA_ROWS], al ; rows (not 'rows-1' !)
  5789                              <1> 	; write_word(BIOSMEM_SEG,BIOSMEM_PAGE_SIZE, rows * cols * 2);
  5790                              <1> 	;mov	ah, [CRT_COLS]
  5791                              <1> 	;mul	ah
  5792                              <1> 	; 17/11/2020
  5793 000030D9 F625[7C660000]      <1> 	mul	byte [CRT_COLS]
  5794 000030DF 66D1E0              <1> 	shl	ax, 1
  5795 000030E2 66A3[186B0100]      <1> 	mov 	[CRT_LEN], ax	
  5796 000030E8 C3                  <1> 	retn
  5797                              <1> 
  5798                              <1> load_text_8_14_pat:
  5799                              <1> 	; 26/07/2016
  5800                              <1> 	; 25/07/2016
  5801                              <1> 	; 23/07/2016
  5802                              <1> 	; 09/07/2016
  5803                              <1> 	; load user defined (EGA/VGA) text fonts
  5804                              <1> 	;
  5805                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5806                              <1> 	; vgabios-0.7a (2011)
  5807                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5808                              <1> 	; 'vgabios.c', 'biosfn_load_text_8_14_pat'
  5809                              <1> 
  5810                              <1> 	; biosfn_load_text_8_14_pat (AL,BL)
  5811                              <1> 
  5812                              <1> 	; get_font_access();
  5813                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5814                              <1> 	; for(i=0;i<0x100;i++)
  5815                              <1> 	; {
  5816                              <1> 	;  src = i * 14;
  5817                              <1> 	;  dest = blockaddr + i * 32;
  5818                              <1> 	;  memcpyb(0xA000, dest, 0xC000, vgafont14+src, 14);
  5819                              <1> 	; }
  5820                              <1> 	; release_font_access();
  5821                              <1> 	; if(AL>=0x10)
  5822                              <1> 	; {
  5823                              <1> 	; set_scan_lines(14);
  5824                              <1> 	; }
  5825                              <1> 
  5826 000030E9 50                  <1> 	push	eax
  5827 000030EA E800FFFFFF          <1> 	call	get_font_access
  5828                              <1> 
  5829                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5830                              <1> 	;mov	dl, bl
  5831                              <1> 	;and	dl, 3
  5832                              <1> 	;shl	dx, 14
  5833                              <1> 	;xchg	dx, bx
  5834                              <1> 	;and	dl, 4
  5835                              <1> 	;shl	dx, 11
  5836                              <1> 	;add	dx, bx 	
  5837                              <1>  
  5838                              <1> 	;xor	dx, dx  ; blockaddr = 0
  5839                              <1> 	; Always block 0 for TRDOS 386 ! (blockaddr=0(
  5840                              <1> 
  5841 000030EF 28DB                <1> 	sub	bl, bl ; i = 0
  5842 000030F1 B70E                <1> 	mov	bh, 14
  5843 000030F3 BE[A03A0100]        <1> 	mov	esi, vgafont14
  5844 000030F8 BF00000A00          <1> 	mov	edi, 0A0000h		
  5845                              <1> lt8_14_1:
  5846                              <1> 	;mov	al, bl
  5847                              <1> 	;mul	bh
  5848                              <1> 	;movzx	esi, ax
  5849                              <1> 	;add	esi, vgafont14
  5850                              <1> 	;mov	al, bl
  5851                              <1> 	;sub	ah, ah
  5852                              <1> 	;shl	ax, 5 ; * 32
  5853                              <1> 	;;add	ax, dx ; blockaddr + i * 32;
  5854                              <1> 	;movzx	edi, ax ; dest
  5855                              <1> 	;add	edi, 0A0000h
  5856 000030FD 0FB6CF              <1> 	movzx	ecx, bh 		
  5857 00003100 F3A4                <1> 	rep	movsb
  5858 00003102 83C712              <1> 	add	edi, 18 ; 32 - 14
  5859 00003105 FEC3                <1> 	inc	bl
  5860 00003107 75F4                <1> 	jnz	short lt8_14_1	
  5861                              <1> 	;
  5862 00003109 E816FFFFFF          <1> 	call	release_font_access
  5863                              <1> 	;
  5864 0000310E 58                  <1> 	pop	eax
  5865                              <1> 	; if(AL>=0x10)
  5866 0000310F 3C10                <1> 	cmp	al, 10h
  5867 00003111 7205                <1> 	jb	short lt8_14_4
  5868                              <1> 	; BH = 14
  5869                              <1>    	; set_scan_lines(14);
  5870 00003113 E84BFFFFFF          <1> 	call	set_scan_lines
  5871                              <1> lt8_14_4:
  5872 00003118 C3                  <1> 	retn
  5873                              <1> 
  5874                              <1> load_text_8_8_pat:
  5875                              <1> 	; 26/07/2016
  5876                              <1> 	; 25/07/2016
  5877                              <1> 	; 23/07/2016
  5878                              <1> 	; 09/07/2016
  5879                              <1> 	; load user defined (EGA/VGA) text fonts
  5880                              <1> 	;
  5881                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5882                              <1> 	; vgabios-0.7a (2011)
  5883                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5884                              <1> 	; 'vgabios.c', 'biosfn_load_text_8_8_pat'
  5885                              <1> 
  5886                              <1> 	; biosfn_load_text_8_8_pat (AL,BL)
  5887                              <1> 
  5888                              <1> 	; get_font_access();
  5889                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5890                              <1> 	; for(i=0;i<0x100;i++)
  5891                              <1> 	; {
  5892                              <1> 	;  src = i * 8;
  5893                              <1> 	;  dest = blockaddr + i * 32;
  5894                              <1> 	;  memcpyb(0xA000, dest, 0xC000, vgafont8+src, 8);
  5895                              <1> 	; }
  5896                              <1> 	; release_font_access();
  5897                              <1> 	; if(AL>=0x10)
  5898                              <1> 	; {
  5899                              <1> 	; set_scan_lines(8);
  5900                              <1> 	; }
  5901                              <1> 
  5902 00003119 50                  <1> 	push	eax
  5903 0000311A E8D0FEFFFF          <1> 	call	get_font_access
  5904                              <1> 
  5905                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5906                              <1> 	;mov	dl, bl
  5907                              <1> 	;and	dl, 3
  5908                              <1> 	;shl	dx, 14
  5909                              <1> 	;xchg	dx, bx
  5910                              <1> 	;and	dl, 4
  5911                              <1> 	;shl	dx, 11
  5912                              <1> 	;add	dx, bx 	
  5913                              <1>  
  5914                              <1> 	;xor	dx, dx  ; blockaddr = 0
  5915                              <1> 	; Always block 0 for TRDOS 386 ! (blockaddr=0(
  5916                              <1> 
  5917 0000311F 28DB                <1> 	sub	bl, bl ; i = 0
  5918 00003121 B708                <1> 	mov	bh, 8
  5919 00003123 BE[A0320100]        <1> 	mov	esi, vgafont8
  5920 00003128 BF00000A00          <1> 	mov	edi, 0A0000h		
  5921                              <1> lt8_8_1:
  5922                              <1> 	;mov	al, bl
  5923                              <1> 	;mul	bh
  5924                              <1> 	;movzx	esi, ax
  5925                              <1> 	;add	esi, vgafont8
  5926                              <1> 	;mov	al, bl
  5927                              <1> 	;sub	ah, ah
  5928                              <1> 	;shl	ax, 5 ; * 32
  5929                              <1> 	;;add	ax, dx ; blockaddr + i * 32;
  5930                              <1> 	;movzx	edi, ax ; dest
  5931                              <1> 	;add	edi, 0A0000h
  5932 0000312D 0FB6CF              <1> 	movzx	ecx, bh 		
  5933 00003130 F3A4                <1> 	rep	movsb
  5934 00003132 83C718              <1> 	add	edi, 24 ; 32 - 8
  5935 00003135 FEC3                <1> 	inc	bl
  5936 00003137 75F4                <1> 	jnz	short lt8_8_1	
  5937                              <1> 	;
  5938 00003139 E8E6FEFFFF          <1> 	call	release_font_access
  5939                              <1> 	;
  5940 0000313E 58                  <1> 	pop	eax
  5941                              <1> 	; if(AL>=0x10)
  5942 0000313F 3C10                <1> 	cmp	al, 10h
  5943 00003141 7205                <1> 	jb	short lt8_8_2
  5944                              <1> 	; BH = 8
  5945                              <1>    	; set_scan_lines(8);
  5946 00003143 E81BFFFFFF          <1> 	call	set_scan_lines
  5947                              <1> lt8_8_2:
  5948 00003148 C3                  <1> 	retn
  5949                              <1> 
  5950                              <1> load_text_8_16_pat:
  5951                              <1> 	; 26/07/2016
  5952                              <1> 	; 25/07/2016
  5953                              <1> 	; 23/07/2016
  5954                              <1> 	; 09/07/2016
  5955                              <1> 	; load user defined (EGA/VGA) text fonts
  5956                              <1> 	;
  5957                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  5958                              <1> 	; vgabios-0.7a (2011)
  5959                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  5960                              <1> 	; 'vgabios.c', 'biosfn_load_text_8_16_pat'
  5961                              <1> 
  5962                              <1> 	; biosfn_load_text_8_16_pat (AL,BL)
  5963                              <1> 
  5964                              <1> 	; get_font_access();
  5965                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5966                              <1> 	; for(i=0;i<0x100;i++)
  5967                              <1> 	; {
  5968                              <1> 	;  src = i * 16;
  5969                              <1> 	;  dest = blockaddr + i * 32;
  5970                              <1> 	;  memcpyb(0xA000, dest, 0xC000, vgafont16+src, 16);
  5971                              <1> 	; }
  5972                              <1> 	; release_font_access();
  5973                              <1> 	; if(AL>=0x10)
  5974                              <1> 	; {
  5975                              <1> 	; set_scan_lines(16);
  5976                              <1> 	; }
  5977                              <1> 
  5978 00003149 50                  <1> 	push	eax
  5979 0000314A E8A0FEFFFF          <1> 	call	get_font_access
  5980                              <1> 
  5981                              <1> 	; blockaddr = ((BL & 0x03) << 14) + ((BL & 0x04) << 11);
  5982                              <1> 	;mov	dl, bl
  5983                              <1> 	;and	dl, 3
  5984                              <1> 	;shl	dx, 14
  5985                              <1> 	;xchg	dx, bx
  5986                              <1> 	;and	dl, 4
  5987                              <1> 	;shl	dx, 11
  5988                              <1> 	;add	dx, bx 	
  5989                              <1>  
  5990                              <1> 	;xor	dx, dx  ; blockaddr = 0
  5991                              <1> 	; Always block 0 for TRDOS 386 ! (blockaddr=0)
  5992                              <1> 
  5993 0000314F 28DB                <1> 	sub	bl, bl ; i = 0
  5994 00003151 B710                <1> 	mov	bh, 16
  5995 00003153 BE[A0480100]        <1> 	mov	esi, vgafont16
  5996 00003158 BF00000A00          <1> 	mov	edi, 0A0000h
  5997 0000315D 0FB6C7              <1> 	movzx	eax, bh	
  5998                              <1> lt8_16_1:
  5999                              <1> 	;mov	al, bl
  6000                              <1> 	;mul	bh
  6001                              <1> 	;movzx	esi, ax
  6002                              <1> 	;add	esi, vgafont16
  6003                              <1> 	;mov	al, bl ; i
  6004                              <1> 	;sub	ah, ah
  6005                              <1> 	;shl	ax, 5 ; * 32
  6006                              <1> 	;;add	ax, dx ; blockaddr + i * 32;
  6007                              <1> 	;movzx	edi, ax ; dest
  6008                              <1> 	;add	edi, 0A0000h
  6009                              <1> 	;movzx	ecx, bh
  6010 00003160 89C1                <1> 	mov	ecx, eax ; 16	
  6011 00003162 F3A4                <1> 	rep	movsb
  6012 00003164 01C7                <1> 	add	edi, eax ; add edi, 16
  6013 00003166 FEC3                <1> 	inc	bl
  6014 00003168 75F6                <1> 	jnz	short lt8_16_1
  6015                              <1> 	;
  6016 0000316A E8B5FEFFFF          <1> 	call	release_font_access
  6017                              <1> 	;
  6018 0000316F 58                  <1> 	pop	eax
  6019                              <1> 	; if(AL>=0x10)
  6020 00003170 3C10                <1> 	cmp	al, 10h
  6021 00003172 7205                <1> 	jb	short lt8_16_2
  6022                              <1> 	; BH = 16
  6023                              <1>    	; set_scan_lines(16);
  6024 00003174 E8EAFEFFFF          <1> 	call	set_scan_lines
  6025                              <1> lt8_16_2:
  6026 00003179 C3                  <1> 	retn
  6027                              <1> 
  6028                              <1> load_gfx_user_chars:
  6029                              <1> 	; 08/08/2016
  6030                              <1> 	; 10/07/2016
  6031                              <1> 	; Setup User-Defined Font for Graphics Mode (VGA)
  6032                              <1> 	;
  6033                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6034                              <1> 	; vgabios-0.7a (2011)
  6035                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6036                              <1> 	; 'vgabios.c', 'biosfn_load_gfx_user_chars'
  6037                              <1> 
  6038                              <1> 	; biosfn_load_gfx_user_chars (ES,BP,CX,BL,DL)
  6039                              <1> 	; /* set 0x43 INT pointer */
  6040                              <1>     	; write_word(0x0, 0x43*4, BP);
  6041                              <1>     	; write_word(0x0, 0x43*4+2, ES);
  6042 0000317A 31C0                <1> 	xor	eax, eax
  6043 0000317C 48                  <1> 	dec	eax ; 0FFFFFFFFh (user defined fonts)
  6044 0000317D A3[2A6B0100]        <1> 	mov	[VGA_INT43H], eax
  6045                              <1> 		
  6046                              <1> 	; BL   screen rows code: 00H = user-specified (in DL)
  6047                              <1>         ;                        01H = 14 rows
  6048                              <1>         ;                        02H = 25 rows
  6049                              <1>         ;                        03H = 43 rows
  6050                              <1>         ; CX   bytes per character definition
  6051                              <1>         ; DL   (when BL=0) custom number of character rows on screen
  6052                              <1> 	; dh = 0 -> 256 characters
  6053                              <1> 	; dh = 80h -> 128 characters
  6054                              <1> 	; (If DH <> 0 and DH <> 80h -> invalid)     	 
  6055                              <1>         ; EBP  address of font-definition information (user's mem space)
  6056                              <1> 
  6057                              <1> 	; switch (BL) {
  6058                              <1> 	; case 0:
  6059                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, DL-1);
  6060                              <1> 	;    break;
  6061 00003182 20DB                <1> 	and	bl, bl
  6062 00003184 7508                <1> 	jnz	short l_gfx_uc_1
  6063 00003186 8815[82660000]      <1> 	mov	[VGA_ROWS], dl  ; not DL-1 !
  6064 0000318C EB23                <1> 	jmp	short l_gfx_uc_4 	
  6065                              <1> l_gfx_uc_1:
  6066                              <1> 	; case 1:
  6067                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 13);
  6068                              <1> 	;    break;
  6069 0000318E FECB                <1> 	dec	bl
  6070 00003190 7509                <1> 	jnz	short l_gfx_uc_2
  6071                              <1> 	; bl = 1
  6072 00003192 C605[82660000]0E    <1> 	mov	byte [VGA_ROWS], 14  ; not 13 !
  6073 00003199 EB16                <1> 	jmp	short l_gfx_uc_4 	
  6074                              <1> l_gfx_uc_2:
  6075 0000319B FECB                <1> 	dec	bl
  6076 0000319D 740B                <1> 	jz	short l_gfx_uc_3 ; bl = 2
  6077 0000319F FECB                <1> 	dec	bl
  6078 000031A1 750E                <1> 	jnz	short l_gfx_uc_4 ; bl > 3
  6079                              <1> 	; bl = 3
  6080                              <1> 	; case 3:
  6081                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 42);
  6082                              <1> 	;    break;
  6083 000031A3 C605[82660000]2B    <1> 	mov	byte [VGA_ROWS], 43  ; not 42 !
  6084                              <1> l_gfx_uc_3:
  6085                              <1>     	; case 2:
  6086                              <1>     	; default:
  6087                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 24);
  6088                              <1> 	;    break;
  6089                              <1> 	; bl = 2 or bl > 3
  6090 000031AA C605[82660000]19    <1> 	mov	byte [VGA_ROWS], 25  ; not 24 !	
  6091                              <1>     	; }
  6092                              <1> l_gfx_uc_4:
  6093                              <1>     	; write_byte(BIOSMEM_SEG, BIOSMEM_CHAR_HEIGHT, CX);
  6094 000031B1 880D[7E660000]      <1> 	mov	[CHAR_HEIGHT], cl
  6095                              <1> 	; }
  6096 000031B7 C3                  <1> 	retn	
  6097                              <1> 
  6098                              <1> load_gfx_8_14_chars:
  6099                              <1> 	; 08/08/2016
  6100                              <1> 	; 10/07/2016
  6101                              <1> 	; Setup ROM 8x14 Font for Graphics Mode (VGA)
  6102                              <1> 	;
  6103                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6104                              <1> 	; vgabios-0.7a (2011)
  6105                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6106                              <1> 	; 'vgabios.c', 'biosfn_load_gfx_8_14_chars'
  6107                              <1> 
  6108                              <1> 	; biosfn_load_gfx_8_14_chars (BL)
  6109                              <1> 	; /* set 0x43 INT pointer */
  6110                              <1>     	; write_word(0x0, 0x43*4, &vgafont14);
  6111                              <1>     	; write_word(0x0, 0x43*4+2, 0xC000);
  6112 000031B8 C705[2A6B0100]-     <1> 	mov	dword [VGA_INT43H], vgafont14
  6112 000031BE [A03A0100]          <1>
  6113                              <1> 		
  6114                              <1> 	; BL    screen rows code: 00H = user-specified (in DL)
  6115                              <1>         ;                         01H = 14 rows
  6116                              <1>         ;                         02H = 25 rows
  6117                              <1>         ;                         03H = 43 rows
  6118                              <1>         ; DL    (when BL=0) custom number of char rows on screen
  6119                              <1> 
  6120                              <1> 	; switch (BL) {
  6121                              <1> 	; case 0:
  6122                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, DL-1);
  6123                              <1> 	;    break;
  6124 000031C2 20DB                <1> 	and	bl, bl
  6125 000031C4 7508                <1> 	jnz	short l_gfx_8_14c_1
  6126 000031C6 8815[82660000]      <1> 	mov	[VGA_ROWS], dl  ; not DL-1 !
  6127 000031CC EB23                <1> 	jmp	short l_gfx_8_14c_4 	
  6128                              <1> l_gfx_8_14c_1:
  6129                              <1> 	; case 1:
  6130                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 13);
  6131                              <1> 	;    break;
  6132 000031CE FECB                <1> 	dec	bl
  6133 000031D0 7509                <1> 	jnz	short l_gfx_8_14c_2
  6134                              <1> 	; bl = 1
  6135 000031D2 C605[82660000]0E    <1> 	mov	byte [VGA_ROWS], 14  ; not 13 !
  6136 000031D9 EB16                <1> 	jmp	short l_gfx_8_14c_4 	
  6137                              <1> l_gfx_8_14c_2:
  6138 000031DB FECB                <1> 	dec	bl
  6139 000031DD 740B                <1> 	jz	short l_gfx_8_14c_3 ; bl = 2
  6140 000031DF FECB                <1> 	dec	bl
  6141 000031E1 750E                <1> 	jnz	short l_gfx_8_14c_4 ; bl > 3
  6142                              <1> 	; bl = 3
  6143                              <1> 	; case 3:
  6144                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 42);
  6145                              <1> 	;    break;
  6146 000031E3 C605[82660000]2B    <1> 	mov	byte [VGA_ROWS], 43  ; not 42 !
  6147                              <1> l_gfx_8_14c_3:
  6148                              <1>     	; case 2:
  6149                              <1>     	; default:
  6150                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 24);
  6151                              <1> 	;    break;
  6152                              <1> 	; bl = 2 or bl > 3
  6153 000031EA C605[82660000]19    <1> 	mov	byte [VGA_ROWS], 25  ; not 24 !	
  6154                              <1>     	; }
  6155                              <1> l_gfx_8_14c_4:
  6156                              <1>     	; write_byte(BIOSMEM_SEG, BIOSMEM_CHAR_HEIGHT, 14);
  6157 000031F1 C605[7E660000]0E    <1>         mov     byte [CHAR_HEIGHT], 14
  6158                              <1> 	; }
  6159 000031F8 C3                  <1> 	retn	
  6160                              <1> 
  6161                              <1> load_gfx_8_8_chars:
  6162                              <1> 	; 08/08/2016
  6163                              <1> 	; 10/07/2016
  6164                              <1> 	; Setup ROM 8x14 Font for Graphics Mode (VGA)
  6165                              <1> 	;
  6166                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6167                              <1> 	; vgabios-0.7a (2011)
  6168                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6169                              <1> 	; 'vgabios.c', 'biosfn_load_gfx_8_8_dd_chars'
  6170                              <1> 
  6171                              <1> 	; biosfn_load_gfx_8_8_dd_chars (BL)
  6172                              <1> 	; /* set 0x43 INT pointer */
  6173                              <1>     	; write_word(0x0, 0x43*4, &vgafont8);
  6174                              <1>     	; write_word(0x0, 0x43*4+2, 0xC000);
  6175 000031F9 C705[2A6B0100]-     <1> 	mov	dword [VGA_INT43H], vgafont8
  6175 000031FF [A0320100]          <1>
  6176                              <1> 		
  6177                              <1> 	; BL    screen rows code: 00H = user-specified (in DL)
  6178                              <1>         ;                         01H = 14 rows
  6179                              <1>         ;                         02H = 25 rows
  6180                              <1>         ;                         03H = 43 rows
  6181                              <1>         ; DL    (when BL=0) custom number of char rows on screen
  6182                              <1> 
  6183                              <1> 	; switch (BL) {
  6184                              <1> 	; case 0:
  6185                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, DL-1);
  6186                              <1> 	;    break;
  6187 00003203 20DB                <1> 	and	bl, bl
  6188 00003205 7508                <1> 	jnz	short l_gfx_8_8c_1
  6189 00003207 8815[82660000]      <1> 	mov	[VGA_ROWS], dl  ; not DL-1 !
  6190 0000320D EB23                <1> 	jmp	short l_gfx_8_8c_4 	
  6191                              <1> l_gfx_8_8c_1:
  6192                              <1> 	; case 1:
  6193                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 13);
  6194                              <1> 	;    break;
  6195 0000320F FECB                <1> 	dec	bl
  6196 00003211 7509                <1> 	jnz	short l_gfx_8_8c_2
  6197                              <1> 	; bl = 1
  6198 00003213 C605[82660000]0E    <1> 	mov	byte [VGA_ROWS], 14  ; not 13 !
  6199 0000321A EB16                <1> 	jmp	short l_gfx_8_8c_4 	
  6200                              <1> l_gfx_8_8c_2:
  6201 0000321C FECB                <1> 	dec	bl
  6202 0000321E 740B                <1> 	jz	short l_gfx_8_8c_3 ; bl = 2
  6203 00003220 FECB                <1> 	dec	bl
  6204 00003222 750E                <1> 	jnz	short l_gfx_8_8c_4 ; bl > 3
  6205                              <1> 	; bl = 3
  6206                              <1> 	; case 3:
  6207                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 42);
  6208                              <1> 	;    break;
  6209 00003224 C605[82660000]2B    <1> 	mov	byte [VGA_ROWS], 43  ; not 42 !
  6210                              <1> l_gfx_8_8c_3:
  6211                              <1>     	; case 2:
  6212                              <1>     	; default:
  6213                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 24);
  6214                              <1> 	;    break;
  6215                              <1> 	; bl = 2 or bl > 3
  6216 0000322B C605[82660000]19    <1> 	mov	byte [VGA_ROWS], 25  ; not 24 !	
  6217                              <1>     	; }
  6218                              <1> l_gfx_8_8c_4:
  6219                              <1>     	; write_byte(BIOSMEM_SEG, BIOSMEM_CHAR_HEIGHT, 8);
  6220 00003232 C605[7E660000]08    <1>         mov     byte [CHAR_HEIGHT], 8
  6221                              <1> 	; }
  6222 00003239 C3                  <1> 	retn
  6223                              <1> 
  6224                              <1> load_gfx_8_16_chars:
  6225                              <1> 	; 08/08/2016
  6226                              <1> 	; 10/07/2016
  6227                              <1> 	; Setup ROM 8x14 Font for Graphics Mode (VGA)
  6228                              <1> 	;
  6229                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6230                              <1> 	; vgabios-0.7a (2011)
  6231                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6232                              <1> 	; 'vgabios.c', 'biosfn_load_gfx_8_16_chars'
  6233                              <1> 
  6234                              <1> 	; biosfn_load_gfx_8_16_chars (BL)
  6235                              <1> 	; /* set 0x43 INT pointer */
  6236                              <1>     	; write_word(0x0, 0x43*4, &vgafont16);
  6237                              <1>     	; write_word(0x0, 0x43*4+2, 0xC000);
  6238 0000323A C705[2A6B0100]-     <1> 	mov	dword [VGA_INT43H], vgafont16
  6238 00003240 [A0480100]          <1>
  6239                              <1> 		
  6240                              <1> 	; BL    screen rows code: 00H = user-specified (in DL)
  6241                              <1>         ;                         01H = 14 rows
  6242                              <1>         ;                         02H = 25 rows
  6243                              <1>         ;                         03H = 43 rows
  6244                              <1>         ; DL    (when BL=0) custom number of char rows on screen
  6245                              <1> 
  6246                              <1> 	; switch (BL) {
  6247                              <1> 	; case 0:
  6248                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, DL-1);
  6249                              <1> 	;    break;
  6250 00003244 20DB                <1> 	and	bl, bl
  6251 00003246 7508                <1> 	jnz	short l_gfx_8_16c_1
  6252 00003248 8815[82660000]      <1> 	mov	[VGA_ROWS], dl  ; not DL-1 !
  6253 0000324E EB23                <1> 	jmp	short l_gfx_8_16c_4 	
  6254                              <1> l_gfx_8_16c_1:
  6255                              <1> 	; case 1:
  6256                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 13);
  6257                              <1> 	;    break;
  6258 00003250 FECB                <1> 	dec	bl
  6259 00003252 7509                <1> 	jnz	short l_gfx_8_16c_2
  6260                              <1> 	; bl = 1
  6261 00003254 C605[82660000]0E    <1> 	mov	byte [VGA_ROWS], 14  ; not 13 !
  6262 0000325B EB16                <1> 	jmp	short l_gfx_8_16c_4 	
  6263                              <1> l_gfx_8_16c_2:
  6264 0000325D FECB                <1> 	dec	bl
  6265 0000325F 740B                <1> 	jz	short l_gfx_8_16c_3 ; bl = 2
  6266 00003261 FECB                <1> 	dec	bl
  6267 00003263 750E                <1> 	jnz	short l_gfx_8_16c_4 ; bl > 3
  6268                              <1> 	; bl = 3
  6269                              <1> 	; case 3:
  6270                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 42);
  6271                              <1> 	;    break;
  6272 00003265 C605[82660000]2B    <1> 	mov	byte [VGA_ROWS], 43  ; not 42 !
  6273                              <1> l_gfx_8_16c_3:
  6274                              <1>     	; case 2:
  6275                              <1>     	; default:
  6276                              <1> 	;    write_byte(BIOSMEM_SEG,BIOSMEM_NB_ROWS, 24);
  6277                              <1> 	;    break;
  6278                              <1> 	; bl = 2 or bl > 3
  6279 0000326C C605[82660000]19    <1> 	mov	byte [VGA_ROWS], 25  ; not 24 !	
  6280                              <1>     	; }
  6281                              <1> l_gfx_8_16c_4:
  6282                              <1>     	; write_byte(BIOSMEM_SEG, BIOSMEM_CHAR_HEIGHT, 16);
  6283 00003273 C605[7E660000]10    <1>         mov     byte [CHAR_HEIGHT], 16
  6284                              <1> 	; }
  6285 0000327A C3                  <1> 	retn
  6286                              <1> 			
  6287                              <1> get_font_info:
  6288                              <1> 	; 19/09/2016
  6289                              <1> 	; 08/08/2016
  6290                              <1> 	; 10/07/2016
  6291                              <1> 	; Get Current Character Generator Info (VGA)
  6292                              <1> 	;
  6293                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6294                              <1> 	; vgabios-0.7a (2011)
  6295                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6296                              <1> 	; 'vgabios.c', 'biosfn_get_font_info'
  6297                              <1> 
  6298                              <1> 	; Modified for TRDOS 386 !
  6299                              <1> 	;
  6300                              <1> 	; INPUT ->
  6301                              <1> 	;    AX = 1130h
  6302                              <1> 	;    BL = 0 -> Get info for current VGA font
  6303                              <1> 	;	       (BH = unused)
  6304                              <1> 	;    19/09/2016
  6305                              <1> 	;    BL > 0 -> Get requested character font data
  6306                              <1> 	;	 BL = 1 -> vgafont8
  6307                              <1> 	;        BL = 2 -> vgafont14
  6308                              <1> 	;	 BL = 3 -> vgafont16   
  6309                              <1> 	;	 BL > 3 -> Invalid function (for now!)
  6310                              <1> 	;	 BH = ASCII code of the first character
  6311                              <1> 	;	 ECX = Number of characters from the 1st char
  6312                              <1> 	;	 ECX >= 256 -> All (256-BH) characters
  6313                              <1> 	;	 ECX = 0 -> All characters (BH = unused)	
  6314                              <1> 	;        EDX = User's Buffer Address	
  6315                              <1> 	; OUTPUT ->
  6316                              <1> 	;    AL = height (scanlines), bytes per character
  6317                              <1> 	;    AH = screen rows
  6318                              <1> 	;    Byte 16-23 of EAX = number of columns
  6319                              <1> 	;    Byte 24-31 of EAX = 
  6320                              <1> 	;	  0 -> default font (not configured yet)
  6321                              <1> 	;	  0FFh -> user defined font
  6322                              <1> 	;	  14 = vgafont14
  6323                              <1> 	;	   8 = vgafont8
  6324                              <1> 	;	  16 = vgafont16
  6325                              <1> 	;   If BL input > 0 -> 
  6326                              <1> 	;       EAX = Actual transfer count
  6327                              <1> 	;
  6328 0000327B 20DB                <1> 	and	bl, bl
  6329 0000327D 7408                <1> 	jz	short gfi_0
  6330                              <1> 	; invalid function (input)
  6331 0000327F 80FB03              <1> 	cmp	bl, 3
  6332 00003282 7642                <1> 	jna	short gfi_4
  6333 00003284 31C0                <1> 	xor	eax, eax ; 0
  6334 00003286 C3                  <1> 	retn
  6335                              <1> gfi_0:
  6336 00003287 A0[7E660000]        <1> 	mov	al, [CHAR_HEIGHT]
  6337 0000328C 8A25[82660000]      <1> 	mov	ah, [VGA_ROWS]
  6338 00003292 C1E010              <1> 	shl	eax, 16
  6339 00003295 A0[7C660000]        <1> 	mov	al, [CRT_COLS]
  6340 0000329A 8B0D[2A6B0100]      <1> 	mov	ecx, [VGA_INT43H]
  6341 000032A0 21C9                <1> 	and	ecx, ecx
  6342 000032A2 741E                <1> 	jz	short gfi_2 ; 0 = default font
  6343 000032A4 41                  <1> 	inc	ecx ; 0FFFFFFFFh -> 0 (user defined font)
  6344 000032A5 7504                <1> 	jnz	short gfi_1
  6345 000032A7 FECC                <1> 	dec	ah ; 0FFh
  6346 000032A9 EB17                <1> 	jmp	short gfi_2
  6347                              <1> gfi_1:
  6348 000032AB 49                  <1> 	dec	ecx ; 08/08/2016
  6349 000032AC B40E                <1> 	mov	ah, 14
  6350 000032AE 81F9[A03A0100]      <1> 	cmp	ecx, vgafont14
  6351 000032B4 740C                <1> 	je	short gfi_2
  6352 000032B6 B408                <1> 	mov	ah, 8
  6353 000032B8 81F9[A0320100]      <1> 	cmp	ecx, vgafont8
  6354 000032BE 7402                <1> 	je	short gfi_2
  6355                              <1> 	; vgafont16
  6356 000032C0 D0E4                <1> 	shl	ah, 1 ; ah = 16
  6357                              <1> gfi_2:
  6358 000032C2 C1C010              <1> 	rol	eax, 16
  6359                              <1> gfi_3:
  6360 000032C5 C3                  <1> 	retn
  6361                              <1> gfi_4:
  6362 000032C6 89D7                <1> 	mov	edi, edx ; **
  6363 000032C8 80FB02              <1> 	cmp	bl, 2
  6364 000032CB 720B                <1> 	jb	short gfi_5
  6365 000032CD 772F                <1> 	ja	short gfi_7
  6366                              <1> 	;BL = 2 -> vgafont14
  6367 000032CF BE[A03A0100]        <1> 	mov	esi, vgafont14 ; *
  6368 000032D4 B30E                <1> 	mov	bl, 14
  6369 000032D6 EB07                <1> 	jmp	short gfi_6 
  6370                              <1> gfi_5:
  6371                              <1> 	;BL = 1 -> vgafont8
  6372 000032D8 BE[A0320100]        <1> 	mov	esi, vgafont8 ; *
  6373 000032DD B308                <1> 	mov	bl, 8
  6374                              <1> gfi_6:
  6375 000032DF 09C9                <1> 	or	ecx, ecx
  6376 000032E1 7424                <1> 	jz	short gfi_8 ; all chars from the 00h
  6377 000032E3 88F8                <1> 	mov	al, bh ; character index
  6378 000032E5 F6E3                <1> 	mul	bl ; char index * char height/size
  6379 000032E7 0FB7D0              <1> 	movzx	edx, ax
  6380 000032EA 01D6                <1> 	add	esi, edx ; *
  6381 000032EC 66BAFF00            <1> 	mov	dx, 255
  6382 000032F0 28FA                <1> 	sub	dl, bh
  6383 000032F2 6642                <1> 	inc	dx	
  6384 000032F4 39D1                <1> 	cmp	ecx, edx
  6385 000032F6 770F                <1> 	ja	short gfi_8
  6386 000032F8 7412                <1> 	je	short gfi_9
  6387 000032FA 89D1                <1> 	mov	ecx, edx
  6388 000032FC EB0E                <1> 	jmp	short gfi_9
  6389                              <1> gfi_7:
  6390                              <1> 	;BL = 3 -> vgafont16
  6391 000032FE BE[A0480100]        <1> 	mov	esi, vgafont16 ; *
  6392 00003303 B310                <1> 	mov	bl, 16
  6393 00003305 EBD8                <1> 	jmp	short gfi_6
  6394                              <1> gfi_8:
  6395 00003307 B900010000          <1> 	mov	ecx, 256
  6396                              <1> gfi_9:
  6397 0000330C 6689C8              <1> 	mov	ax, cx ; character count
  6398 0000330F 30FF                <1> 	xor	bh, bh
  6399 00003311 66F7E3              <1> 	mul	bx ; char count * char height/size	
  6400 00003314 6689C1              <1>  	mov	cx, ax
  6401                              <1> 
  6402                              <1> 	; ESI = source address in system space
  6403                              <1> 	; EDI = user's buffer address
  6404                              <1> 	; ECX = transfer (byte) count
  6405 00003317 E846BA0000          <1> 	call	transfer_to_user_buffer
  6406 0000331C 89C8                <1> 	mov	eax, ecx ; actual transfer count
  6407 0000331E C3                  <1> 	retn
  6408                              <1> 	
  6409                              <1> vga_pal_funcs:
  6410                              <1> 	; 10/08/2016
  6411                              <1> 	; VGA Palette functions
  6412                              <1> 	;
  6413                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
  6414                              <1> 	; vgabios-0.7a (2011)
  6415                              <1> 	; by the LGPL VGABios developers Team (2001-2008)
  6416                              <1> 	; 'vgabios.c', 'vgarom.asm'
  6417                              <1> 
  6418 0000331F 3C00                <1> 	cmp	al, 0
  6419 00003321 0F848F000000        <1>         je      set_single_palette_reg
  6420                              <1> vga_palf_1001:
  6421 00003327 3C01                <1> 	cmp	al, 1
  6422 00003329 0F84B4000000        <1>         je      set_overscan_border_color
  6423                              <1> vga_palf_1002:
  6424 0000332F 3C02                <1> 	cmp	al, 2
  6425 00003331 0F84B0000000        <1>         je      set_all_palette_reg
  6426                              <1> vga_palf_1003:
  6427 00003337 3C03                <1> 	cmp	al, 3
  6428 00003339 0F84E8000000        <1>         je      toggle_intensity
  6429                              <1> vga_palf_1007:
  6430 0000333F 3C07                <1> 	cmp	al, 7
  6431 00003341 0F840D010000        <1>         je      get_single_palette_reg
  6432 00003347 7266                <1> 	jb	short vga_palf_unknown
  6433                              <1> vga_palf_1008:
  6434 00003349 3C08                <1> 	cmp	al, 8
  6435 0000334B 0F8437010000        <1>         je      read_overscan_border_color
  6436                              <1> vga_palf_1009:
  6437 00003351 3C09                <1> 	cmp	al, 9
  6438 00003353 0F8433010000        <1> 	je	get_all_palette_reg
  6439                              <1> vga_palf_1010:
  6440 00003359 3C10                <1> 	cmp	al, 10h
  6441 0000335B 0F8487010000        <1> 	je 	set_single_dac_reg
  6442 00003361 724C                <1> 	jb	short vga_palf_unknown
  6443                              <1> vga_palf_1012:
  6444 00003363 3C12                <1> 	cmp	al, 12h
  6445 00003365 0F8498010000        <1>         je      set_all_dac_reg
  6446 0000336B 7242                <1> 	jb	short vga_palf_unknown
  6447                              <1> vga_palf_1013:
  6448 0000336D 3C13                <1> 	cmp	al, 13h
  6449 0000336F 0F84CC010000        <1>         je      select_video_dac_color_page
  6450                              <1> vga_palf_1015:
  6451 00003375 3C15                <1> 	cmp	al, 15h
  6452 00003377 0F8412020000        <1> 	je	read_single_dac_reg
  6453 0000337D 7230                <1> 	jb	short vga_palf_unknown
  6454                              <1> vga_palf_1017:
  6455 0000337F 3C17                <1> 	cmp	al, 17h
  6456 00003381 0F8428020000        <1>         je      read_all_dac_reg
  6457 00003387 7226                <1> 	jb	short vga_palf_unknown
  6458                              <1> vga_palf_1018:
  6459 00003389 3C18                <1> 	cmp	al, 18h
  6460 0000338B 0F845E020000        <1>         je      set_pel_mask
  6461                              <1> vga_palf_1019:
  6462 00003391 3C19                <1> 	cmp	al, 19h
  6463 00003393 0F8462020000        <1>         je      read_pel_mask
  6464                              <1> vga_palf_101A:
  6465 00003399 3C1A                <1> 	cmp	al, 1Ah
  6466 0000339B 0F8468020000        <1>         je      read_video_dac_state
  6467                              <1> vga_palf_101B:
  6468 000033A1 3C1B                <1> 	cmp	al, 1Bh
  6469                              <1> 	;jne	short vga_palf_unknown
  6470 000033A3 770A                <1> 	ja	short vga_palf_unknown
  6471                              <1>  
  6472 000033A5 E80EF7FFFF          <1> 	call	gray_scale_summing
  6473 000033AA E9A7E5FFFF          <1>         jmp     VIDEO_RETURN 	
  6474                              <1> 
  6475                              <1> vga_palf_unknown:
  6476 000033AF 29C0                <1> 	sub	eax, eax ; 0 = invalid function
  6477 000033B1 E9A5E5FFFF          <1>         jmp     _video_return
  6478                              <1> 
  6479                              <1> set_single_palette_reg:
  6480                              <1> 	; 10/08/2016
  6481                              <1> 	; Set One Palette Register
  6482                              <1> 	; BL = register number to set
  6483                              <1> 	;     (a 4-bit attribute nibble: 00h-0Fh)
  6484                              <1> 	; BH = 6-bit RGB color to display 
  6485                              <1> 	;      for that attribute
  6486                              <1> 
  6487 000033B6 80FB14              <1> 	cmp	bl, 14h
  6488                              <1> 	;ja	short no_actl_reg1
  6489 000033B9 0F8797E5FFFF        <1> 	ja	VIDEO_RETURN
  6490 000033BF 6650                <1> 	push	ax
  6491 000033C1 6652                <1> 	push	dx
  6492 000033C3 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6493 000033C7 EC                  <1> 	in	al, dx
  6494 000033C8 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6495 000033CC 88D8                <1> 	mov	al, bl
  6496 000033CE EE                  <1> 	out	dx, al
  6497 000033CF 88F8                <1> 	mov	al, bh
  6498 000033D1 EE                  <1> 	out	dx, al
  6499 000033D2 B020                <1> 	mov	al, 20h
  6500 000033D4 EE                  <1> 	out	dx, al
  6501                              <1> 	; ifdef VBOX
  6502 000033D5 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6503 000033D9 EC                  <1> 	in	al, dx
  6504                              <1> 	; endif ; VBOX
  6505 000033DA 665A                <1> 	pop	dx
  6506 000033DC 6658                <1> 	pop	ax
  6507                              <1> ;no_actl_reg1:
  6508 000033DE E973E5FFFF          <1> 	jmp	VIDEO_RETURN
  6509                              <1> 
  6510                              <1> set_overscan_border_color:
  6511                              <1> 	; 10/08/2016
  6512                              <1> 	; Set Overscan/Border Color Register
  6513                              <1> 	; BH = 6-bit RGB color to display 
  6514                              <1> 	;      for that attribute
  6515                              <1> 	
  6516 000033E3 B311                <1> 	mov	bl, 11h
  6517 000033E5 EBCF                <1>   	jmp	short set_single_palette_reg
  6518                              <1> 
  6519                              <1> set_all_palette_reg:
  6520                              <1> 	; 10/08/2016
  6521                              <1> 	; Set All Palette Registers and Overscan
  6522                              <1> 	; EDX = Address of 17 bytes; 
  6523                              <1> 	; an rgbRGB value for each of 16 palette
  6524                              <1> 	; registers plus one for the border.
  6525                              <1> 
  6526 000033E7 89D6                <1> 	mov	esi, edx ; user buffer
  6527 000033E9 B911000000          <1> 	mov	ecx, 17
  6528 000033EE 89E7                <1> 	mov	edi, esp
  6529 000033F0 83EC14              <1> 	sub	esp, 20	 	 
  6530 000033F3 E8B4B90000          <1> 	call	transfer_from_user_buffer
  6531                              <1> 	;jc	VIDEO_RETURN
  6532                              <1> 
  6533 000033F8 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6534 000033FC EC                  <1> 	in	al, dx
  6535 000033FD B100                <1> 	mov	cl, 0
  6536 000033FF 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6537                              <1> set_palette_loop:
  6538 00003403 88C8                <1> 	mov	al, cl
  6539 00003405 EE                  <1> 	out	dx, al
  6540 00003406 8A07                <1> 	mov	al, [edi]
  6541 00003408 EE                  <1> 	out	dx, al
  6542 00003409 47                  <1> 	inc	edi
  6543 0000340A FEC1                <1> 	inc	cl
  6544 0000340C 80F910              <1> 	cmp	cl, 10h
  6545 0000340F 75F2                <1> 	jne	short set_palette_loop
  6546 00003411 B011                <1> 	mov	al, 11h
  6547 00003413 EE                  <1> 	out	dx, al
  6548 00003414 8A07                <1> 	mov	al, [edi]
  6549 00003416 EE                  <1> 	out	dx, al
  6550 00003417 B020                <1> 	mov	al, 20h
  6551 00003419 EE                  <1> 	out	dx, al
  6552                              <1> 	; ifdef VBOX
  6553 0000341A 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6554 0000341E EC                  <1> 	in	al, dx
  6555                              <1> 	; endif ; VBOX
  6556 0000341F 83C414              <1> 	add	esp, 20
  6557 00003422 E92FE5FFFF          <1> 	jmp	VIDEO_RETURN
  6558                              <1> 
  6559                              <1> toggle_intensity:
  6560                              <1> 	; 10/08/2016
  6561                              <1> 	; Select Foreground Blink or Bold Background
  6562                              <1> 	; BL = 00h = enable bold backgrounds
  6563                              <1> 	;	    (16 background colors)
  6564                              <1>         ;      01h = enable blinking foreground
  6565                              <1> 	;	    (8 background colors)
  6566                              <1> 
  6567 00003427 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6568 0000342B EC                  <1> 	in	al, dx
  6569 0000342C 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6570 00003430 B010                <1> 	mov	al, 10h
  6571 00003432 EE                  <1> 	out	dx, al
  6572 00003433 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6573 00003437 EC                  <1> 	in	al, dx
  6574 00003438 24F7                <1> 	and	al, 0F7h
  6575 0000343A 80E301              <1> 	and	bl, 01h
  6576 0000343D C0E303              <1> 	shl	bl, 3
  6577 00003440 08D8                <1> 	or	al, bl
  6578 00003442 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6579 00003446 EE                  <1> 	out	dx, al
  6580 00003447 B020                <1> 	mov	al, 20h
  6581 00003449 EE                  <1> 	out	dx, al
  6582                              <1> 	; ifdef VBOX
  6583 0000344A 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6584 0000344E EC                  <1> 	in	al, dx
  6585                              <1> 	; endif ; VBOX
  6586 0000344F E902E5FFFF          <1> 	jmp	VIDEO_RETURN
  6587                              <1> 
  6588                              <1> get_single_palette_reg:
  6589                              <1> 	; 10/08/2016
  6590                              <1> 	; Read One Palette Register
  6591                              <1>         ; INPUT:
  6592                              <1> 	; BL = Palette register to read (00h-0Fh)
  6593                              <1> 	; OUTPUT:
  6594                              <1> 	; BH = Current rgbRGB value of specified register
  6595                              <1> 	;      for that attribute
  6596                              <1> 
  6597 00003454 80FB14              <1> 	cmp	bl, 14h
  6598                              <1> 	;ja	short no_actl_reg2
  6599 00003457 0F87F9E4FFFF        <1> 	ja	VIDEO_RETURN
  6600                              <1> 
  6601 0000345D 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6602 00003461 EC                  <1> 	in	al, dx
  6603 00003462 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6604 00003466 88D8                <1> 	mov	al, bl
  6605 00003468 EE                  <1> 	out	dx, al
  6606 00003469 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6607 0000346D EC                  <1> 	in	al, dx
  6608 0000346E 8844240D            <1> 	mov	[esp+13], al ; bh
  6609 00003472 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6610 00003476 EC                  <1> 	in	al, dx
  6611 00003477 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6612 0000347B B020                <1> 	mov	al, 20h
  6613 0000347D EE                  <1> 	out	dx, al
  6614                              <1> 	; ifdef VBOX
  6615 0000347E 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6616 00003482 EC                  <1> 	in	al, dx
  6617                              <1> 	; endif ; VBOX
  6618 00003483 E9CEE4FFFF          <1> 	jmp	VIDEO_RETURN
  6619                              <1> 
  6620                              <1> read_overscan_border_color:
  6621                              <1> 	; 10/08/2016
  6622                              <1> 	; Read Overscan Register
  6623                              <1> 	; OUTPUT:
  6624                              <1> 	; BH = current rgbRGB value 
  6625                              <1> 	;      of the overscan/border register
  6626                              <1> 
  6627 00003488 B311                <1> 	mov	bl, 11h
  6628 0000348A EBC8                <1> 	jmp	short get_single_palette_reg
  6629                              <1> 
  6630                              <1> get_all_palette_reg:
  6631                              <1> 	; 10/08/2016
  6632                              <1> 	; Read All Palette Registers
  6633                              <1> 	; EDX = Address of 17-byte buffer 
  6634                              <1> 	;	to receive data
  6635                              <1> 	
  6636 0000348C 89D7                <1> 	mov	edi, edx
  6637 0000348E 89E3                <1> 	mov	ebx, esp
  6638 00003490 89DE                <1> 	mov	esi, ebx
  6639 00003492 83EC14              <1> 	sub	esp, 20	 
  6640                              <1> 
  6641 00003495 B100                <1> 	mov	cl, 0
  6642                              <1> get_palette_loop:
  6643 00003497 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6644 0000349B EC                  <1> 	in	al, dx
  6645 0000349C 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6646 000034A0 88C8                <1> 	mov	al, cl
  6647 000034A2 EE                  <1> 	out	dx, al
  6648 000034A3 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6649 000034A7 EC                  <1> 	in	al, dx
  6650 000034A8 8803                <1> 	mov	[ebx], al
  6651 000034AA 43                  <1> 	inc	ebx
  6652 000034AB FEC1                <1> 	inc	cl
  6653 000034AD 80F910              <1> 	cmp	cl, 10h
  6654 000034B0 75E5                <1> 	jne	short get_palette_loop
  6655 000034B2 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6656 000034B6 EC                  <1> 	in	al, dx
  6657 000034B7 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6658 000034BB B011                <1> 	mov	al, 11h
  6659 000034BD EE                  <1> 	out	dx, al
  6660 000034BE 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6661 000034C2 EC                  <1> 	in	al, dx
  6662 000034C3 8803                <1> 	mov	[ebx], al
  6663 000034C5 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6664 000034C9 EC                  <1> 	in	al, dx
  6665 000034CA 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6666 000034CE B020                <1> 	mov	al, 20h
  6667 000034D0 EE                  <1> 	out	dx, al
  6668                              <1> 	; ifdef VBOX
  6669 000034D1 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6670 000034D5 EC                  <1> 	in	al, dx
  6671                              <1> 	; endif ; VBOX
  6672                              <1> 
  6673 000034D6 B911000000          <1> 	mov	ecx, 17 ; transfer (byte) count
  6674                              <1> 	; ESI = source address in system space
  6675                              <1> 	; EDI = user's buffer address
  6676 000034DB E882B80000          <1> 	call	transfer_to_user_buffer
  6677                              <1> 
  6678 000034E0 83C414              <1> 	add	esp, 20
  6679 000034E3 E96EE4FFFF          <1> 	jmp	VIDEO_RETURN
  6680                              <1> 
  6681                              <1> set_single_dac_reg:
  6682                              <1> 	; 10/08/2016
  6683                              <1> 	; Set One DAC Color Register
  6684                              <1> 	; BX = color register to set (0-255)
  6685                              <1>         ; CH = green value (00h-3Fh)
  6686                              <1>         ; CL = blue value  (00h-3Fh)
  6687                              <1>         ; DH = red value   (00h-3Fh)
  6688                              <1> 
  6689 000034E8 6652                <1> 	push	dx
  6690 000034EA 66BAC803            <1> 	mov	dx, 3C8h ; VGAREG_DAC_WRITE_ADDRESS
  6691 000034EE 88D8                <1> 	mov	al, bl
  6692 000034F0 EE                  <1> 	out	dx, al
  6693                              <1> 	;mov	dx, 3C9h ; VGAREG_DAC_DATA
  6694 000034F1 6642                <1> 	inc	dx
  6695 000034F3 6658                <1> 	pop	ax
  6696 000034F5 88E0                <1> 	mov	al, ah
  6697 000034F7 EE                  <1> 	out	dx, al
  6698 000034F8 88E8                <1> 	mov	al, ch
  6699 000034FA EE                  <1> 	out	dx, al
  6700 000034FB 88C8                <1> 	mov	al, cl
  6701 000034FD EE                  <1> 	out	dx, al
  6702 000034FE E953E4FFFF          <1> 	jmp	VIDEO_RETURN
  6703                              <1> 
  6704                              <1> set_all_dac_reg:
  6705                              <1> 	; 12/08/2016
  6706                              <1> 	; 11/08/2016
  6707                              <1> 	; 10/08/2016
  6708                              <1> 	; Set a Block of DAC Color Register
  6709                              <1> 	; BX = first DAC register to set (0-00FFh)
  6710                              <1> 	; ECX = number of registers to set (0-00FFh)
  6711                              <1> 	; EDX = addr of a table of R,G,B values 
  6712                              <1> 	;	(it will be CX*3 bytes long)
  6713                              <1> 
  6714 00003503 89D6                <1> 	mov	esi, edx ; user buffer
  6715 00003505 89CA                <1> 	mov	edx, ecx
  6716 00003507 66D1E1              <1> 	shl	cx, 1 ; *2
  6717 0000350A 01D1                <1> 	add	ecx, edx ; ecx = 3*ecx
  6718 0000350C 89E5                <1> 	mov	ebp, esp
  6719 0000350E 89EF                <1> 	mov	edi, ebp
  6720 00003510 29CF                <1> 	sub	edi, ecx
  6721 00003512 6683E7FC            <1> 	and	di, 0FFFCh ; (dword alignment)
  6722 00003516 89FC                <1> 	mov	esp, edi
  6723 00003518 E88FB80000          <1> 	call	transfer_from_user_buffer
  6724                              <1> 	;jc	VIDEO_RETURN
  6725                              <1> 
  6726 0000351D 89D1                <1> 	mov	ecx, edx
  6727 0000351F 66BAC803            <1> 	mov	dx, 3C8h ; VGAREG_DAC_WRITE_ADDRESS
  6728 00003523 88D8                <1> 	mov	al, bl
  6729 00003525 EE                  <1> 	out	dx, al
  6730 00003526 66BAC903            <1> 	mov	dx, 3C9h ; VGAREG_DAC_DATA
  6731                              <1> set_dac_loop:
  6732 0000352A 8A07                <1> 	mov	al, [edi]
  6733 0000352C EE                  <1> 	out	dx, al
  6734 0000352D 47                  <1> 	inc	edi
  6735 0000352E 8A07                <1> 	mov	al, [edi]
  6736 00003530 EE                  <1> 	out	dx, al
  6737 00003531 47                  <1> 	inc	edi
  6738 00003532 8A07                <1> 	mov	al, [edi]
  6739 00003534 EE                  <1> 	out	dx, al
  6740 00003535 47                  <1> 	inc	edi
  6741 00003536 6649                <1> 	dec	cx
  6742 00003538 75F0                <1> 	jnz	short set_dac_loop
  6743 0000353A 89EC                <1> 	mov	esp, ebp
  6744 0000353C E915E4FFFF          <1> 	jmp	VIDEO_RETURN
  6745                              <1> 
  6746                              <1> select_video_dac_color_page:
  6747                              <1> 	; 10/08/2016
  6748                              <1> 	; DAC Color Paging Functions
  6749                              <1> 	; BL = 00H = select color paging mode
  6750                              <1>         ;       BH = paging mode
  6751                              <1>         ;            00h = 4 blocks of 64 registers
  6752                              <1>         ;            01h = 16 blocks of 16 registers
  6753                              <1> 	; BL = 01H = activate color page
  6754                              <1>         ;       BH = DAC color page number
  6755                              <1>         ;            00h-03h (4-page/64-reg mode)
  6756                              <1>         ;            00h-0Fh (16-page/16-reg mode)
  6757                              <1> 
  6758 00003541 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6759 00003545 EC                  <1> 	in	al, dx
  6760 00003546 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6761 0000354A B010                <1> 	mov	al, 10h
  6762 0000354C EE                  <1> 	out	dx, al
  6763 0000354D 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6764 00003551 EC                  <1> 	in	al, dx
  6765 00003552 80E301              <1> 	and	bl, 01h
  6766 00003555 750E                <1> 	jnz	short set_dac_page
  6767 00003557 247F                <1> 	and	al, 07Fh
  6768 00003559 C0E707              <1> 	shl	bh, 7
  6769 0000355C 08F8                <1> 	or	al, bh
  6770 0000355E 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6771 00003562 EE                  <1> 	out	dx, al
  6772 00003563 EB1D                <1> 	jmp	short set_actl_normal
  6773                              <1> set_dac_page:
  6774 00003565 6650                <1> 	push	ax
  6775 00003567 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6776 0000356B EC                  <1> 	in	al, dx
  6777 0000356C 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6778 00003570 B014                <1> 	mov	al, 14h
  6779 00003572 EE                  <1> 	out	dx, al
  6780 00003573 6658                <1> 	pop	ax
  6781 00003575 2480                <1> 	and	al, 80h
  6782 00003577 7503                <1> 	jnz	short set_dac_16_page
  6783 00003579 C0E702              <1> 	shl	bh, 2
  6784                              <1> set_dac_16_page:
  6785 0000357C 80E70F              <1> 	and	bh, 0Fh
  6786 0000357F 88F8                <1> 	mov	al, bh
  6787 00003581 EE                  <1> 	out	dx, al
  6788                              <1> set_actl_normal:
  6789 00003582 B020                <1> 	mov	al, 20h
  6790 00003584 EE                  <1> 	out	dx, al
  6791                              <1> 	; ifdef VBOX
  6792 00003585 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6793 00003589 EC                  <1> 	in	al, dx
  6794                              <1> 	; endif ; VBOX
  6795 0000358A E9C7E3FFFF          <1> 	jmp	VIDEO_RETURN	
  6796                              <1> 
  6797                              <1> read_single_dac_reg:
  6798                              <1> 	; 10/08/2016
  6799                              <1> 	; Read One DAC Color Register
  6800                              <1> 	; INPUT:
  6801                              <1> 	; BX = color register to read (0-255)
  6802                              <1> 	; OUTPUT:
  6803                              <1> 	; CH = green value (00h-3Fh)
  6804                              <1>         ; CL = blue value  (00h-3Fh)
  6805                              <1>         ; DH = red value   (00h-3Fh)
  6806                              <1> 
  6807 0000358F 66BAC703            <1> 	mov	dx, 3C7h ; VGAREG_DAC_READ_ADDRESS
  6808 00003593 88D8                <1> 	mov	al, bl
  6809 00003595 EE                  <1> 	out	dx, al
  6810 00003596 66BAC903            <1> 	mov	dx, 3C9h ; VGAREG_DAC_DATA
  6811 0000359A EC                  <1> 	in	al, dx
  6812 0000359B 88442415            <1> 	mov	[esp+21], al ; dh
  6813 0000359F EC                  <1> 	in	al, dx
  6814 000035A0 88C5                <1> 	mov	ch, al
  6815 000035A2 EC                  <1> 	in	al, dx
  6816 000035A3 88C1                <1> 	mov	cl, al
  6817 000035A5 66894C2410          <1> 	mov	[esp+16], cx ; cx
  6818 000035AA E9A7E3FFFF          <1> 	jmp	VIDEO_RETURN	
  6819                              <1> 
  6820                              <1> read_all_dac_reg:
  6821                              <1> 	; 12/08/2016
  6822                              <1> 	; 11/08/2016
  6823                              <1> 	; 10/08/2016
  6824                              <1> 	; Read a Block of DAC Color Registers
  6825                              <1>         ; BX = first DAC register to read (0-00FFh)
  6826                              <1>         ; ECX = number of registers to read (0-00FFh)
  6827                              <1>         ; EDX = addr of a buffer to hold R,G,B values
  6828                              <1> 	;	(CX*3 bytes long)
  6829                              <1> 
  6830 000035AF 89D7                <1> 	mov	edi, edx ; user buffer
  6831 000035B1 89CA                <1> 	mov	edx, ecx
  6832 000035B3 66D1E2              <1> 	shl	dx, 1 ; *2
  6833 000035B6 01CA                <1> 	add	edx, ecx ; edx = 3*ecx
  6834 000035B8 89E5                <1> 	mov	ebp, esp
  6835 000035BA 89EE                <1> 	mov	esi, ebp
  6836 000035BC 29D6                <1> 	sub	esi, edx
  6837 000035BE 6683E6FC            <1> 	and	si, 0FFFCh ; (dword alignment)
  6838 000035C2 89F4                <1> 	mov	esp, esi
  6839 000035C4 52                  <1> 	push	edx ; 3*ecx
  6840 000035C5 66BAC703            <1> 	mov	dx, 3C7h ; VGAREG_DAC_READ_ADDRESS
  6841 000035C9 88D8                <1> 	mov	al, bl
  6842 000035CB EE                  <1> 	out	dx, al
  6843 000035CC 66BAC903            <1> 	mov	dx, 3C9h ; VGAREG_DAC_DATA
  6844 000035D0 89F3                <1> 	mov	ebx, esi
  6845                              <1> read_dac_loop:
  6846 000035D2 EC                  <1> 	in	al, dx
  6847 000035D3 8803                <1> 	mov	[ebx], al
  6848 000035D5 43                  <1> 	inc	ebx
  6849 000035D6 EC                  <1> 	in	al, dx
  6850 000035D7 8803                <1> 	mov	[ebx], al
  6851 000035D9 43                  <1> 	inc	ebx
  6852 000035DA EC                  <1> 	in	al, dx
  6853 000035DB 8803                <1> 	mov	[ebx], al
  6854 000035DD 43                  <1> 	inc	ebx
  6855 000035DE 6649                <1> 	dec	cx
  6856 000035E0 75F0                <1> 	jnz	short read_dac_loop
  6857 000035E2 59                  <1> 	pop	ecx ; 3*ecx
  6858                              <1> 	; ECX = transfer (byte) count
  6859                              <1> 	; ESI = source address in system space
  6860                              <1> 	; EDI = user's buffer address
  6861 000035E3 E87AB70000          <1> 	call	transfer_to_user_buffer
  6862 000035E8 89EC                <1> 	mov	esp, ebp
  6863 000035EA E967E3FFFF          <1> 	jmp	VIDEO_RETURN
  6864                              <1> 
  6865                              <1> set_pel_mask:
  6866                              <1> 	; 10/08/2016
  6867                              <1> 	; BL = mask value
  6868 000035EF 66BAC603            <1> 	mov	dx, 3C6h ; VGAREG_PEL_MASK
  6869 000035F3 88D8                <1> 	mov	al, bl
  6870 000035F5 EE                  <1> 	out	dx, al
  6871 000035F6 E95BE3FFFF          <1> 	jmp	VIDEO_RETURN
  6872                              <1> 
  6873                              <1> read_pel_mask:
  6874                              <1> 	; 10/08/2016
  6875                              <1> 	; Output: BL = mask value 
  6876 000035FB 66BAC603            <1> 	mov	dx, 3C6h ; VGAREG_PEL_MASK
  6877 000035FF EC                  <1> 	in	al, dx
  6878 00003600 8844240C            <1> 	mov	[esp+12], al ; bl
  6879 00003604 E94DE3FFFF          <1> 	jmp	VIDEO_RETURN
  6880                              <1> 
  6881                              <1> read_video_dac_state:
  6882                              <1> 	; 10/08/2016
  6883                              <1> 	; Query DAC Color Paging State
  6884                              <1> 	; Output:
  6885                              <1> 	; BH = current active DAC color page
  6886                              <1>         ; BL = current active DAC paging mode
  6887                              <1> 
  6888 00003609 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6889 0000360D EC                  <1> 	in	al, dx
  6890 0000360E 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6891 00003612 B010                <1> 	mov	al, 10h
  6892 00003614 EE                  <1> 	out	dx, al
  6893 00003615 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6894 00003619 EC                  <1> 	in	al, dx
  6895 0000361A 88C3                <1> 	mov	bl, al
  6896 0000361C C0EB07              <1> 	shr	bl, 7
  6897 0000361F 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6898 00003623 EC                  <1> 	in	al, dx
  6899 00003624 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6900 00003628 B014                <1> 	mov	al, 14h
  6901 0000362A EE                  <1> 	out	dx, al
  6902 0000362B 66BAC103            <1> 	mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  6903 0000362F EC                  <1> 	in	al, dx
  6904 00003630 88C7                <1> 	mov	bh, al
  6905 00003632 80E70F              <1> 	and	bh, 0Fh
  6906 00003635 F6C301              <1> 	test	bl, 01
  6907 00003638 7503                <1> 	jnz	short get_dac_16_page
  6908 0000363A C0EF02              <1> 	shr	bh, 2
  6909                              <1> get_dac_16_page:
  6910 0000363D 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6911 00003641 EC                  <1> 	in	al, dx
  6912 00003642 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  6913 00003646 B020                <1> 	mov	al, 20h
  6914 00003648 EE                  <1> 	out	dx, al
  6915                              <1> 	; ifdef VBOX
  6916 00003649 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  6917 0000364D EC                  <1> 	in	al, dx
  6918                              <1> 	; endif ; VBOX 
  6919 0000364E 66895C240C          <1> 	mov	[esp+12], bx ; bx
  6920 00003653 E9FEE2FFFF          <1> 	jmp	VIDEO_RETURN
  6921                              <1> 
  6922                              <1> ; 23/11/2020 - TRDOS 386 v2.0.3
  6923                              <1> ; VBE 2 BOCHS/QEMU emulator extensions 
  6924                              <1> ;	for TRDOS 386 v2 kernel (video bios)  
  6925                              <1> 
  6926                              <1> ; BOCH/QEMU VBE2 VGA BIOS code 
  6927                              <1> ;	by Jeroen Janssen (2002)
  6928                              <1> ;	by Volker Rupper (2003-2020)
  6929                              <1> ; vbe.c (02/01/2020) 
  6930                              <1> 
  6931                              <1> ; vbe.h (02/01/2020)
  6932                              <1> 
  6933                              <1> VBE_DISPI_BANK_ADDRESS	equ	0A0000h
  6934                              <1> VBE_DISPI_BANK_SIZE_KB	equ	64
  6935                              <1> 
  6936                              <1> VBE_DISPI_MAX_XRES	equ	2560
  6937                              <1> VBE_DISPI_MAX_YRES	equ	1600
  6938                              <1> 
  6939                              <1> VBE_DISPI_IOPORT_INDEX	equ	01CEh
  6940                              <1> VBE_DISPI_IOPORT_DATA	equ	01CFh
  6941                              <1> 
  6942                              <1> VBE_DISPI_INDEX_ID	equ	00h
  6943                              <1> VBE_DISPI_INDEX_XRES	equ	01h
  6944                              <1> VBE_DISPI_INDEX_YRES	equ	02h
  6945                              <1> VBE_DISPI_INDEX_BPP	equ	03h
  6946                              <1> VBE_DISPI_INDEX_ENABLE	equ	04h
  6947                              <1> VBE_DISPI_INDEX_BANK	equ	05h
  6948                              <1> VBE_DISPI_INDEX_VIRT_WIDTH equ	06h
  6949                              <1> VBE_DISPI_INDEX_VIRT_HEIGHT equ	07h
  6950                              <1> VBE_DISPI_INDEX_X_OFFSET equ	08h
  6951                              <1> VBE_DISPI_INDEX_Y_OFFSET equ	09h
  6952                              <1> VBE_DISPI_INDEX_VIDEO_MEMORY_64K equ 0Ah
  6953                              <1> VBE_DISPI_INDEX_DDC	equ	0Bh
  6954                              <1> 
  6955                              <1> VBE_DISPI_ID0		equ	0B0C0h
  6956                              <1> VBE_DISPI_ID1		equ	0B0C1h
  6957                              <1> VBE_DISPI_ID2		equ	0B0C2h
  6958                              <1> VBE_DISPI_ID3		equ	0B0C3h
  6959                              <1> VBE_DISPI_ID4		equ	0B0C4h
  6960                              <1> VBE_DISPI_ID5		equ	0B0C5h
  6961                              <1> 
  6962                              <1> VBE_DISPI_DISABLED	equ	00h
  6963                              <1> VBE_DISPI_ENABLED	equ	01h
  6964                              <1> VBE_DISPI_GETCAPS	equ	02h
  6965                              <1> VBE_DISPI_8BIT_DAC	equ	20h
  6966                              <1> VBE_DISPI_LFB_ENABLED	equ	40h
  6967                              <1> VBE_DISPI_NOCLEARMEM	equ	80h
  6968                              <1> 
  6969                              <1> VBE_DISPI_LFB_PHYSICAL_ADDRESS equ 0E0000000h
  6970                              <1> 
  6971                              <1> ; ***
  6972                              <1> 
  6973                              <1> ;// VBE Return Status Info
  6974                              <1> ;// AL
  6975                              <1> VBE_RETURN_STATUS_SUPPORTED	equ	4Fh
  6976                              <1> VBE_RETURN_STATUS_UNSUPPORTED	equ	00h
  6977                              <1> ;// AH
  6978                              <1> VBE_RETURN_STATUS_SUCCESSFULL	equ	00h
  6979                              <1> VBE_RETURN_STATUS_FAILED	equ	01h
  6980                              <1> VBE_RETURN_STATUS_NOT_SUPPORTED	equ	02h
  6981                              <1> VBE_RETURN_STATUS_INVALID	equ	03h
  6982                              <1> 
  6983                              <1> ;// VBE Mode Numbers
  6984                              <1> 
  6985                              <1> VBE_MODE_VESA_DEFINED		equ	0100h
  6986                              <1> VBE_MODE_REFRESH_RATE_USE_CRTC	equ	0800h
  6987                              <1> VBE_MODE_LINEAR_FRAME_BUFFER	equ	4000h
  6988                              <1> VBE_MODE_PRESERVE_DISPLAY_MEMORY equ	8000h
  6989                              <1> 
  6990                              <1> ;// Mode Attributes
  6991                              <1> 
  6992                              <1> VBE_MODE_ATTRIBUTE_SUPPORTED		   equ	0001h
  6993                              <1> VBE_MODE_ATTRIBUTE_EXTENDED_INFO_AVAILABLE equ	0002h
  6994                              <1> VBE_MODE_ATTRIBUTE_COLOR_MODE		   equ	0008h
  6995                              <1> VBE_MODE_ATTRIBUTE_GRAPHICS_MODE	   equ	0010h
  6996                              <1> VBE_MODE_ATTRIBUTE_LINEAR_FRAME_BUFFER_MODE equ	0080h
  6997                              <1> VBE_MODE_ATTRIBUTE_DOUBLE_SCAN_MODE	   equ	0100h
  6998                              <1> VBE_MODE_ATTRIBUTE_INTERLACE_MODE	   equ	0200h
  6999                              <1> 
  7000                              <1> ;// Window attributes
  7001                              <1> 
  7002                              <1> VBE_WINDOW_ATTRIBUTE_RELOCATABLE equ	01h
  7003                              <1> VBE_WINDOW_ATTRIBUTE_READABLE	 equ	02h
  7004                              <1> VBE_WINDOW_ATTRIBUTE_WRITEABLE	 equ	04h
  7005                              <1> 
  7006                              <1> ;/* Video memory */
  7007                              <1> VGAMEM_GRAPH equ 0A000h
  7008                              <1> VGAMEM_CTEXT equ 0B800h
  7009                              <1> ;VGAMEM_MTEXT equ 0B000h
  7010                              <1> 
  7011                              <1> ;// Memory model
  7012                              <1> 
  7013                              <1> ;VBE_MEMORYMODEL_TEXT_MODE	equ	00h
  7014                              <1> ;VBE_MEMORYMODEL_CGA_GRAPHICS	equ	01h
  7015                              <1> ;VBE_MEMORYMODEL_PLANAR		equ	03h
  7016                              <1> VBE_MEMORYMODEL_PACKED_PIXEL	equ	04h
  7017                              <1> ;VBE_MEMORYMODEL_NON_CHAIN_4_256 equ	05h
  7018                              <1> VBE_MEMORYMODEL_DIRECT_COLOR	equ	06h
  7019                              <1> ;VBE_MEMORYMODEL_YUV		equ	07h
  7020                              <1> 
  7021                              <1> ;// DirectColorModeInfo
  7022                              <1> 
  7023                              <1> ;VBE_DIRECTCOLOR_COLOR_RAMP_PROGRAMMABLE equ 01h
  7024                              <1> VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE equ 02h
  7025                              <1> 
  7026                              <1> VBE_DISPI_TOTAL_VIDEO_MEMORY_MB	equ 16
  7027                              <1> 
  7028                              <1> ; 24/11/2020
  7029                              <1> ; vbe.c
  7030                              <1> 
  7031                              <1> %if 1
  7032                              <1> 
  7033                              <1> ; * (TRDOS 386, INT 31h, VESA Video Bios functions) 
  7034                              <1> ; * ---------------------------------------------------------
  7035                              <1> ; * Function 02h - Set VBE Mode
  7036                              <1> ; * ---------------------------------------------------------
  7037                              <1> ; * Input:
  7038                              <1> ; *		AX = 4F02h
  7039                              <1> ; *		BX = Desired Mode to set
  7040                              <1> ; * Output:
  7041                              <1> ; *		AX = VBE Return Status
  7042                              <1> ; * 
  7043                              <1> ; *----------------------------------------------------------
  7044                              <1> ; *
  7045                              <1> 
  7046                              <1> vbe_biosfn_set_mode:
  7047                              <1> 	; 27/11/2020
  7048                              <1> 	; 25/11/2020
  7049                              <1> 	; 23/11/2020 (TRDOS 386 v2.0.3)
  7050                              <1> 	; (ref: vbe.c, 02/01/2020, vruppert)
  7051                              <1> 	;
  7052                              <1> 	; Input:
  7053                              <1> 	;	bx = video (bios) mode
  7054                              <1> 	;	ax = 4F02h
  7055                              <1> 	; Output:
  7056                              <1> 	;	ax = 004Fh (successful)
  7057                              <1> 	;	ah > 0 -> error
  7058                              <1> 	;
  7059                              <1> 	; Modified registers: eax, ebx, ecx, edx, esi, edi
  7060                              <1> 
  7061                              <1> 	; 27/11/2020
  7062                              <1> 
  7063                              <1> 	;;push	ds  ; *
  7064                              <1> 	;;push	es  ; **
  7065                              <1> 	;;push	ebp ; ***
  7066                              <1> 	;;push	esi ; **** 
  7067                              <1> 	 			
  7068 00003658 57                  <1> 	push	edi ; *****
  7069 00003659 52                  <1> 	push	edx ; ******
  7070 0000365A 51                  <1> 	push	ecx ; *******
  7071 0000365B 53                  <1> 	push	ebx ; ********	
  7072                              <1> 
  7073                              <1> 	;xor	eax, eax
  7074 0000365C 80E7C1              <1> 	and	bh, 0C1h ; use bit 15, 14, 8 only (for bh)
  7075 0000365F 883D[9D110300]      <1> 	mov	[vbe_mode_x], bh
  7076 00003665 80E701              <1> 	and	bh, 1
  7077 00003668 753C                <1> 	jnz	short vbe_sm_3  ; VESA VBE mode
  7078                              <1> 
  7079                              <1>  	;;test	bx, 4000h ; VBE_MODE_LINEAR_FRAME_BUFFER
  7080                              <1> 	;test	bh, 40h
  7081                              <1> 	;jz	short vbe_sm_0
  7082                              <1> 	;; lfb_flag
  7083                              <1> 	;mov	al, 40h	; VBE_DISPI_LFB_ENABLED
  7084                              <1> vbe_sm_0:
  7085                              <1> 	; 27/11/2020
  7086 0000366A B080                <1> 	mov	al, 80h
  7087                              <1> 	;test	bh, 80h ; VBE_MODE_PRESERVE_DISPLAY_MEMORY 	
  7088                              <1> 	;jnz	short vbe_sm_1 ; no_clear
  7089                              <1> 	;; clear
  7090                              <1> 	;sub	al, al ; 0
  7091 0000366C 8405[9D110300]      <1> 	test	[vbe_mode_x], al ; 80h
  7092 00003672 7402                <1> 	jz	short vbe_sm_1 ; clear display memory
  7093                              <1> 	; no_clear
  7094 00003674 08C3                <1> 	or	bl, al ; VBE_MODE_PRESERVE_DISPLAY_MEMORY
  7095                              <1> vbe_sm_1:
  7096                              <1> 	; check non vesa mode
  7097                              <1> 	;;cmp	bx, 100h ; VBE_MODE_VESA_DEFINED
  7098                              <1> 	;;jna	short vbe_sm_2
  7099                              <1> 	;and	bh, 1
  7100                              <1> 	;jnz	short vbe_sm_3 
  7101                              <1> 
  7102                              <1> 	; BX <= 1FFh
  7103                              <1> 
  7104                              <1> 	; 27/11/2020
  7105                              <1> 	;or	bl, al	; al = 80h if no_clear option is set 
  7106                              <1> 	;		; al = 0 if no_clear option is not set 
  7107                              <1> 
  7108                              <1> 	; 25/11/2020
  7109                              <1> 	; VBE DISPI will be disabled in 'biosfn_set_video_mode'
  7110                              <1>  
  7111                              <1> 	;xor	al, al ; 0 ; VBE_DISPI_DISABLED
  7112                              <1> 	;call	dispi_set_enable
  7113                              <1> 
  7114                              <1> 	; call the vgabios in order to set the video mode
  7115                              <1> 	; this allows for going back to textmode with a VBE call
  7116                              <1> 	; (some applications expect that to work)
  7117                              <1> 
  7118                              <1> 	;and	bx, 0FFh
  7119                              <1> 	
  7120                              <1> 	; 27/11/2020
  7121                              <1> biosfn_set_video_mode:
  7122                              <1> 	; _call: call subroutine
  7123                              <1> 	; 26/11/2020 (TRDOS 386 v2.0.3)
  7124                              <1> 	; (ref: vgabios.c, 02/01/2020, vruppert)
  7125                              <1> 	; Input:
  7126                              <1> 	;	bl = VGA video (bios) mode
  7127                              <1> 	; Output:
  7128                              <1> 	;	cf = 1 -> error
  7129                              <1> 	;	cf = 0 -> ok
  7130                              <1> 	;
  7131                              <1> 	; Modified registers: eax, ebx, ecx, edx, esi, edi
  7132                              <1> 
  7133                              <1> 	; 'dispi_set_enable(VBE_DISPI_DISABLED);'
  7134                              <1> 	
  7135                              <1> 	;mov	ax, 0 ; VBE_DISPI_DISABLED 
  7136 00003676 31C0                <1> 	xor	eax, eax ; 0 
  7137 00003678 E8B7000000          <1> 	call	dispi_set_enable
  7138                              <1> 	
  7139 0000367D 88D8                <1> 	mov	al, bl
  7140                              <1> 	;jmp	_set_mode ; (in 'biosfn_set_video_mode' sub)
  7141 0000367F E8E3E2FFFF          <1> 	call	_set_mode ; will return with cf=1 only if
  7142                              <1> 			; desired mode is not implemented
  7143                              <1> 	; _retn: return from subroutine
  7144 00003684 721A                <1> 	jc	short vbe_sm_2 ; 25/11/2020
  7145                              <1> 
  7146                              <1> 	; 26/11/2020
  7147 00003686 31C0                <1> 	xor	eax, eax 
  7148 00003688 A0[7A660000]        <1> 	mov	al, [CRT_MODE]
  7149                              <1> 	; 27/11/2020
  7150 0000368D 8A25[176B0100]      <1> 	mov	ah, [noclearmem] ; 80h or 0
  7151                              <1> 	;and	ah 80h
  7152 00003693 66A3[9E110300]      <1> 	mov	[video_mode], ax ; bit 15 = no_clear flag
  7153                              <1> 				 ; bit 14 = 0 (not LFB model)
  7154                              <1> vbe_sm_ret1:
  7155                              <1> 	; 27/11/2020
  7156 00003699 B04F                <1> 	mov	al, 4Fh ; Function call successful
  7157                              <1> 	; eax = 004Fh
  7158                              <1> vbe_sm_ret2:
  7159 0000369B 5B                  <1> 	pop	ebx ; ********
  7160 0000369C 59                  <1> 	pop	ecx ; *******
  7161 0000369D 5A                  <1> 	pop	edx ; ******
  7162 0000369E 5F                  <1> 	pop	edi ; *****
  7163                              <1> 
  7164                              <1> 	;;pop	esi ; ****
  7165                              <1> 	;;pop	ebp ; ***
  7166                              <1> 	;;pop	es  ; **
  7167                              <1> 	;;pop	ds  ; * 
  7168                              <1> 
  7169 0000369F C3                  <1> 	retn
  7170                              <1> 
  7171                              <1> vbe_sm_2:
  7172                              <1> 	;mov	ax, 0100h ; Function is not supported
  7173                              <1> 	; 27/11/2020
  7174 000036A0 31C0                <1> 	xor	eax, eax
  7175 000036A2 B401                <1> 	mov	ah, 01h
  7176                              <1> 	; eax = 0100h
  7177                              <1> 	;retn
  7178 000036A4 EBF5                <1> 	jmp	short vbe_sm_ret2
  7179                              <1> 
  7180                              <1> vbe_sm_3:
  7181                              <1> 	; 27/11/2020
  7182                              <1> 	; bx = mode (bit 0 to 8)
  7183                              <1> 
  7184                              <1> 	; 25/11/2020
  7185                              <1> 
  7186                              <1> 	; Alternative 2 (instead of 'Mode_info_find_mode')
  7187                              <1> 	;push	edi
  7188 000036A6 E8B1010000          <1> 	call	set_mode_info_list ; (alternative 2)	
  7189                              <1> 	;pop	edi
  7190 000036AB 668B1E              <1> 	mov	bx, [esi] ; mode
  7191                              <1> 
  7192                              <1> 	; Alternative 1 (instead of 'set_mode_info_list')
  7193                              <1> 	;call	mode_info_find_mode ; (alternative 1)
  7194                              <1> 
  7195 000036AE 09F6                <1> 	or	esi, esi
  7196 000036B0 74EE                <1> 	jz	short vbe_sm_2 ; VBE mode number is wrong
  7197                              <1> 			       ; or it is not supported
  7198                              <1> 	; 27/11/2020
  7199 000036B2 0A3D[9D110300]      <1> 	or	bh, [vbe_mode_x]
  7200                              <1> 
  7201                              <1> 	; save VESA VBE mode
  7202 000036B8 66891D[9E110300]    <1> 	mov	[video_mode], bx
  7203                              <1> 		; 27/11/2020
  7204                              <1> 		; bit 0 to 8 = VESA VBE mode
  7205                              <1> 		; bit 9 to 13 = 0 (bit 0 to 13 = mode)
  7206                              <1> 		; bit 14 = Linear/Flat Frame Buffer flag
  7207                              <1> 		; bit 15 = 'memory not cleared
  7208                              <1> 		;	   at last mode set' flag
  7209                              <1> 
  7210                              <1> 	; first disable current mode
  7211                              <1> 	; (when switching between vesa modes)
  7212                              <1> 	; 'dispi_set_enable(VBE_DISPI_DISABLED);'        
  7213                              <1> 
  7214                              <1> 	;mov	ax, VBE_DISPI_DISABLED ; 0
  7215 000036BF 29C0                <1> 	sub	eax, eax ; 0
  7216 000036C1 E86E000000          <1> 	call	dispi_set_enable
  7217                              <1> 
  7218 000036C6 807E1B08            <1> 	cmp	byte [esi+MODEINFO.BitsPerPixel], 8
  7219 000036CA 7509                <1> 	jne	short vbe_sm_4
  7220                              <1> 
  7221                              <1> 	; 'load_dac_palette(3);'
  7222 000036CC 56                  <1> 	push	esi
  7223 000036CD B403                <1> 	mov	ah, 3  ; palette3, 256 colors
  7224 000036CF E891F3FFFF          <1> 	call	load_dac_palette
  7225 000036D4 5E                  <1> 	pop	esi
  7226                              <1> vbe_sm_4:	
  7227                              <1>   	;'dispi_set_bpp(cur_info->info.BitsPerPixel);'
  7228 000036D5 668B461B            <1> 	mov	ax, [esi+MODEINFO.BitsPerPixel]
  7229 000036D9 E86A000000          <1> 	call	dispi_set_bpp
  7230                              <1>         ;'dispi_set_xres(cur_info->info.XResolution);'
  7231 000036DE 668B4614            <1> 	mov	ax, [esi+MODEINFO.XResolution]
  7232 000036E2 E867000000          <1> 	call	dispi_set_xres
  7233                              <1>         ;'dispi_set_yres(cur_info->info.YResolution);'
  7234 000036E7 668B4616            <1> 	mov	ax, [esi+MODEINFO.YResolution]
  7235 000036EB E864000000          <1> 	call	dispi_set_yres
  7236                              <1>         ;'dispi_set_bank(0);'
  7237                              <1> 	;xor	ax, ax
  7238 000036F0 31C0                <1> 	xor	eax, eax ; 0
  7239 000036F2 E863000000          <1> 	call	dispi_set_bank
  7240                              <1>         ;'dispi_set_enable(VBE_DISPI_ENABLED|no_clear|lfb_flag);'
  7241                              <1> 	;mov	ax, di
  7242                              <1> 	; ah = 0 ; 27/11/2020
  7243 000036F7 A0[9D110300]        <1> 	mov	al, [vbe_mode_x] ; restore VBE mode bit 14 & 15
  7244 000036FC 0C01                <1> 	or	al, 1 ; VBE_DISPI_ENABLED
  7245 000036FE E831000000          <1> 	call	dispi_set_enable
  7246                              <1> 
  7247                              <1>         ; 'vga_compat_setup();'
  7248 00003703 E867000000          <1> 	call	vga_compat_setup
  7249                              <1> 
  7250                              <1> 	; 26/11/2020
  7251 00003708 31C0                <1> 	xor	eax, eax
  7252 0000370A FEC8                <1> 	dec	al 
  7253 0000370C A2[7A660000]        <1> 	mov	[CRT_MODE], al ; 0FFh = VESA VBE mode sign
  7254                              <1> 
  7255                              <1> 	; 27/11/2020
  7256 00003711 EB86                <1> 	jmp	short vbe_sm_ret1 ; Function call successful
  7257                              <1> 	
  7258                              <1> 	; 27/11/2020
  7259                              <1> 	;mov	al, 4Fh
  7260                              <1> 	;	; eax = 004Fh = Function call successful
  7261                              <1> 	;jmp	short vbe_sm_ret2
  7262                              <1> 
  7263                              <1> ; * (TRDOS 386, INT 31h, VESA Video Bios functions) 
  7264                              <1> ; * ---------------------------------------------------------
  7265                              <1> ; * Function 03h - Return Current VBE Mode
  7266                              <1> ; * ---------------------------------------------------------
  7267                              <1> ; * Input:
  7268                              <1> ; *		AX = 4F03h
  7269                              <1> ; * Output:
  7270                              <1> ; *		AX = VBE Return Status
  7271                              <1> ; *		BX = Current VBE Mode
  7272                              <1> ; * 
  7273                              <1> ; *----------------------------------------------------------
  7274                              <1> ; *
  7275                              <1> 
  7276                              <1> vbe_biosfn_return_current_mode:
  7277                              <1> 	; 27/11/2020 (TRDOS 386 v2.0.3)
  7278                              <1> 	; (ref: vbe.c, 02/01/2020, vruppert)
  7279                              <1> 	;
  7280                              <1> 	; Input:
  7281                              <1> 	;	none
  7282                              <1> 	; Output:
  7283                              <1> 	;	ax = 004Fh (successful)
  7284                              <1> 	;	ah > 0 -> error
  7285                              <1> 	;	bx = current video (bios) mode (if ah = 0)
  7286                              <1> 	;
  7287                              <1> 	; Modified registers: eax, ebx, ecx, edx, esi, edi
  7288                              <1> 
  7289                              <1> 	; 27/11/2020
  7290                              <1> 
  7291                              <1> 	;;push	ds  ; *
  7292                              <1> 	;;push	es  ; **
  7293                              <1> 	;;push	ebp ; ***
  7294                              <1> 	;;push	esi ; **** 
  7295                              <1> 	 			
  7296 00003713 52                  <1> 	push	edx ; *****
  7297                              <1> 
  7298                              <1> 	; (vbe.c)
  7299                              <1> 	;call	dispi_get_enable
  7300                              <1> 	;	; ax = vbe display interface status
  7301                              <1> 	;and	al, 1 ; VBE_DISPI_ENABLED
  7302                              <1> 	;jnz	short vbe_gm_1  ; VBE graphics mode
  7303                              <1> 
  7304 00003714 A0[7A660000]        <1> 	mov	al, [CRT_MODE] ; current cga/vga mode
  7305 00003719 3CFF                <1> 	cmp	al, 0FFh ; VBE extentension signature
  7306 0000371B 720F                <1> 	jb	short vbe_gm_1 ; get CGA/VGA mode
  7307                              <1> 
  7308                              <1> 	; get VBE mode
  7309                              <1> vbe_gm_0:
  7310 0000371D 66A1[9E110300]      <1> 	mov	ax, [video_mode]
  7311                              <1> 		; BX bits:
  7312                              <1> 		; bit 0 to 8 = VESA VBE video mode
  7313                              <1> 		; bit 9 to 13 = 0 
  7314                              <1> 		; bit 14 = last mode set LFB option
  7315                              <1> 		;	   1 - linear/flat frame buffer
  7316                              <1> 		;	   0 - windowed frame buffer
  7317                              <1> 		; bit 15 = last mode set no_clear option		
  7318                              <1> 		;	   0 - video memory cleared
  7319                              <1> 		;	   1 - video memory not cleared
  7320                              <1> 	
  7321                              <1> vbe_gm_return:
  7322 00003723 5A                  <1> 	pop	edx ; ******
  7323 00003724 0FB7D8              <1> 	movzx	ebx, ax
  7324 00003727 31C0                <1> 	xor	eax, eax ; 0
  7325 00003729 B04F                <1> 	mov	al, 4Fh ; ax = 004Fh (successful)
  7326 0000372B C3                  <1> 	retn	
  7327                              <1> 
  7328                              <1> vbe_gm_1:
  7329                              <1> 	; legacy (old, standard) CGA/VGA bios video mode
  7330 0000372C 8A25[176B0100]      <1> 	mov	ah, [noclearmem] ; 80h or 0
  7331                              <1> 		; BX bits: 
  7332                              <1> 		; bit 0 to 7 = video mode
  7333                              <1> 		; bit 8 to 13 = 0 
  7334                              <1> 		; bit 14 = 0 (not LFB mode) CGA/VGA
  7335                              <1> 		; bit 15 = 1 if [noclearmem] = 80h
  7336                              <1> 		;	   0 if [noclearmem] = 0
  7337 00003732 EBEF                <1> 	jmp	short vbe_gm_return 
  7338                              <1> 
  7339                              <1> dispi_set_enable:
  7340                              <1> 	; 23/11/2020
  7341                              <1> 	; Input:
  7342                              <1> 	;	ax = VBE_DISPI_ENABLED = 1
  7343                              <1> 	;	     or VBE_DISPI_DISABLED = 0
  7344                              <1> 	;
  7345                              <1> 	; Modified registers: none
  7346                              <1> 	
  7347                              <1> 	;push	edx
  7348                              <1> 	;push	eax
  7349                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7350                              <1> 	;mov	ax, 04h	  ; VBE_DISPI_INDEX_ENABLE
  7351                              <1> 	;out	dx, ax
  7352                              <1> 	;pop	eax
  7353                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7354                              <1> 	;;mov	dl, 0CFh
  7355                              <1> 	;inc	dl
  7356                              <1> 	;out	dx, ax
  7357                              <1> 	;pop	edx
  7358                              <1> 	;retn
  7359                              <1> 
  7360                              <1> 	; 25/11/2020
  7361                              <1> 	; Modified registers: edx
  7362                              <1> 	;push	edx
  7363 00003734 66BA0400            <1> 	mov	dx, 04h ; VBE_DISPI_INDEX_ENABLE
  7364                              <1> 	;call	dispi_set_parms
  7365                              <1> 	;pop	edx
  7366                              <1> 	;retn
  7367                              <1> 	;;jmp	short dispi_set_parms
  7368                              <1> 
  7369                              <1> dispi_set_parms:
  7370                              <1> 	; 25/11/2020
  7371                              <1> 	; Input:
  7372                              <1> 	;	ax = data
  7373                              <1> 	;	dx = vbe dispi register index
  7374                              <1> 	;
  7375                              <1> 	; Modified registers: edx
  7376                              <1> 
  7377 00003738 50                  <1> 	push	eax
  7378 00003739 6689D0              <1> 	mov	ax, dx
  7379 0000373C 66BACE01            <1> 	mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7380 00003740 66EF                <1> 	out	dx, ax
  7381 00003742 58                  <1> 	pop	eax
  7382                              <1> 	;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7383                              <1> 	;mov	dl, 0CFh
  7384 00003743 FEC2                <1> 	inc	dl
  7385 00003745 66EF                <1> 	out	dx, ax
  7386 00003747 C3                  <1> 	retn
  7387                              <1> 
  7388                              <1> dispi_set_bpp:
  7389                              <1> 	; 25/11/2020
  7390                              <1> 	; Input:
  7391                              <1> 	;	ax = Bits per pixel value
  7392                              <1> 	;	     (8,16,24,32)
  7393                              <1> 	;
  7394                              <1> 	; Modified registers: none
  7395                              <1> 
  7396                              <1> 	;push	edx
  7397                              <1> 	;push	eax
  7398                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7399                              <1> 	;mov	ax, 03h	  ; VBE_DISPI_INDEX_BPP
  7400                              <1> 	;out	dx, ax
  7401                              <1> 	;pop	eax
  7402                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7403                              <1> 	;;mov	dl, 0CFh
  7404                              <1> 	;inc	dl
  7405                              <1> 	;out	dx, ax
  7406                              <1> 	;pop	edx
  7407                              <1> 	;retn
  7408                              <1> 
  7409                              <1> 	; 25/11/2020
  7410                              <1> 	; Modified registers: edx
  7411                              <1> 	;push	edx
  7412 00003748 66BA0300            <1> 	mov	dx, 03h ; VBE_DISPI_INDEX_BPP
  7413                              <1> 	;call	dispi_set_parms
  7414                              <1> 	;pop	edx
  7415                              <1> 	;retn
  7416 0000374C EBEA                <1> 	jmp	short dispi_set_parms
  7417                              <1> 
  7418                              <1> dispi_set_xres:
  7419                              <1> 	; 25/11/2020
  7420                              <1> 	; Input:
  7421                              <1> 	;	ax = X resolution (screen witdh)
  7422                              <1> 	;	     (320,640,800,1024,1280,1920)
  7423                              <1> 	;
  7424                              <1> 	; Modified registers: none
  7425                              <1> 
  7426                              <1> 	;push	edx
  7427                              <1> 	;push	eax
  7428                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7429                              <1> 	;mov	ax, 01h	  ; VBE_DISPI_INDEX_XRES
  7430                              <1> 	;out	dx, ax
  7431                              <1> 	;pop	eax
  7432                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7433                              <1> 	;;mov	dl, 0CFh
  7434                              <1> 	;inc	dl
  7435                              <1> 	;out	dx, ax
  7436                              <1> 	;pop	edx
  7437                              <1> 	;retn
  7438                              <1> 
  7439                              <1> 	; 25/11/2020
  7440                              <1> 	; Modified registers: edx
  7441                              <1> 	;push	edx
  7442 0000374E 66BA0100            <1> 	mov	dx, 01h ; VBE_DISPI_INDEX_XRES
  7443                              <1> 	;call	dispi_set_parms
  7444                              <1> 	;pop	edx
  7445                              <1> 	;retn
  7446 00003752 EBE4                <1> 	jmp	short dispi_set_parms
  7447                              <1> 
  7448                              <1> dispi_set_yres:
  7449                              <1> 	; 25/11/2020
  7450                              <1> 	; Input:
  7451                              <1> 	;	ax = Y resolution (screen height)
  7452                              <1> 	;	     (200,400,600,720,768,1080)
  7453                              <1> 	;
  7454                              <1> 	; Modified registers: none
  7455                              <1> 
  7456                              <1> 	;push	edx
  7457                              <1> 	;push	eax
  7458                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7459                              <1> 	;mov	ax, 02h	  ; VBE_DISPI_INDEX_YRES
  7460                              <1> 	;out	dx, ax
  7461                              <1> 	;pop	eax
  7462                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7463                              <1> 	;;mov	dl, 0CFh
  7464                              <1> 	;inc	dl
  7465                              <1> 	;out	dx, ax
  7466                              <1> 	;pop	edx
  7467                              <1> 	;retn
  7468                              <1> 
  7469                              <1> 	; 25/11/2020
  7470                              <1> 	; Modified registers: edx
  7471                              <1> 	;push	edx
  7472 00003754 66BA0200            <1> 	mov	dx, 02h  ; VBE_DISPI_INDEX_YRES
  7473                              <1> 	;call	dispi_set_parms
  7474                              <1> 	;pop	edx
  7475                              <1> 	;retn
  7476 00003758 EBDE                <1> 	jmp	short dispi_set_parms
  7477                              <1> 
  7478                              <1> dispi_set_bank:
  7479                              <1> 	; 25/11/2020
  7480                              <1> 	; Input:
  7481                              <1> 	;	ax = video memory bank number
  7482                              <1> 	;
  7483                              <1> 	; Modified registers: none
  7484                              <1> 
  7485                              <1> 	;push	edx
  7486                              <1> 	;push	eax
  7487                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7488                              <1> 	;mov	ax, 05h	  ; VBE_DISPI_INDEX_BANK
  7489                              <1> 	;out	dx, ax
  7490                              <1> 	;pop	eax
  7491                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7492                              <1> 	;;mov	dl, 0CFh
  7493                              <1> 	;inc	dl
  7494                              <1> 	;out	dx, ax
  7495                              <1> 	;pop	edx
  7496                              <1> 	;retn
  7497                              <1> 	
  7498                              <1> 	; 25/11/2020
  7499                              <1> 	; Modified registers: edx
  7500                              <1> 	;push	edx
  7501 0000375A 66BA0500            <1> 	mov	dx, 05h  ; VBE_DISPI_INDEX_BANK
  7502                              <1> 	;call	dispi_set_parms
  7503                              <1> 	;pop	edx
  7504                              <1> 	;retn
  7505 0000375E EBD8                <1> 	jmp	short dispi_set_parms
  7506                              <1> 
  7507                              <1> dispi_get_enable:
  7508                              <1> 	; 27/11/2020
  7509                              <1> 	; Input:
  7510                              <1> 	;	none
  7511                              <1> 	; Output:
  7512                              <1> 	;	ax = vbe dispi status
  7513                              <1> 	;
  7514                              <1> 	; Modified registers: eax
  7515                              <1> 	
  7516                              <1> 	;push	edx
  7517                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7518                              <1> 	;mov	ax, 04h	  ; VBE_DISPI_INDEX_ENABLE
  7519                              <1> 	;out	dx, ax
  7520                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7521                              <1> 	;;mov	dl, 0CFh
  7522                              <1> 	;inc	dl
  7523                              <1> 	;in	ax, dx
  7524                              <1> 	;pop	edx
  7525                              <1> 	;retn
  7526                              <1> 
  7527                              <1> 	; 27/11/2020
  7528                              <1> 	; Modified registers: eax, edx
  7529                              <1> 	;push	edx
  7530 00003760 66B80400            <1> 	mov	ax, 04h ; VBE_DISPI_INDEX_ENABLE
  7531                              <1> 	;call	dispi_get_parms
  7532                              <1> 	;pop	edx
  7533                              <1> 	;retn
  7534                              <1> 	;;jmp	short dispi_get_parms
  7535                              <1> 
  7536                              <1> dispi_get_parms:
  7537                              <1> 	; 25/11/2020
  7538                              <1> 	; Input:
  7539                              <1> 	;	ax = vbe dispi register index
  7540                              <1> 	; output:
  7541                              <1> 	;	ax = data
  7542                              <1> 	;
  7543                              <1> 	; Modified registers: eax, edx
  7544                              <1> 
  7545 00003764 66BACE01            <1> 	mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  7546 00003768 66EF                <1> 	out	dx, ax
  7547                              <1> 	;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  7548                              <1> 	;mov	dl, 0CFh
  7549 0000376A FEC2                <1> 	inc	dl
  7550 0000376C 66ED                <1> 	in	ax, dx
  7551 0000376E C3                  <1> 	retn
  7552                              <1> 
  7553                              <1> vga_compat_setup:
  7554                              <1> 	; 26/11/2020
  7555                              <1> 	; 25/11/2020
  7556                              <1> 	; VGA compatibility setup
  7557                              <1> 	; (vbe.c, 02/01/2020, vruppert)
  7558                              <1> 	;
  7559                              <1> 	; Input:
  7560                              <1> 	;	none
  7561                              <1> 	;
  7562                              <1> 	; Modified registers: eax, edx
  7563                              <1> 	
  7564                              <1> 	; 26/11/2020
  7565                              <1>   	;push	eax
  7566                              <1>   	;push	edx
  7567                              <1> 
  7568                              <1>   	; set CRT X resolution
  7569 0000376F 66BACE01            <1>   	mov	dx, 1CEh ; VBE_DISPI_IOPORT_INDEX
  7570 00003773 66B80100            <1>   	mov	ax, 01h  ; VBE_DISPI_INDEX_XRES
  7571 00003777 66EF                <1>   	out	dx, ax
  7572                              <1>   	;mov	dx, 1CFh ; VBE_DISPI_IOPORT_DATA
  7573 00003779 FEC2                <1>   	inc	dl
  7574 0000377B 66ED                <1> 	in	ax, dx
  7575 0000377D 50                  <1> 	push	eax
  7576 0000377E 66BAD403            <1> 	mov	dx, 3D4h ; VGAREG_VGA_CRTC_ADDRESS
  7577 00003782 66B81100            <1>   	mov	ax, 0011h ; Vertical retrace end register
  7578 00003786 66EF                <1>   	out	dx, ax
  7579                              <1>   	;pop	eax
  7580                              <1>   	;push	eax
  7581 00003788 8B0424              <1>   	mov	eax, [esp]
  7582 0000378B 66C1E803            <1> 	shr	ax, 3 ; / 8 for pixel to character
  7583 0000378F 6648                <1>   	dec	ax  ; - 1 (EGA or VGA?)
  7584 00003791 88C4                <1>   	mov	ah, al
  7585 00003793 B001                <1>   	mov	al, 01h ; Horizontal display end register
  7586 00003795 66EF                <1>   	out	dx, ax
  7587 00003797 58                  <1>   	pop	eax
  7588                              <1> 
  7589 00003798 E8B0000000          <1> 	call	vga_set_virt_width
  7590                              <1> 
  7591                              <1>   	; set CRT Y resolution
  7592 0000379D 66BACE01            <1>   	mov	dx, 1CEh ; VBE_DISPI_IOPORT_INDEX
  7593 000037A1 66B80200            <1>   	mov	ax, 02h  ; VBE_DISPI_INDEX_YRES
  7594 000037A5 66EF                <1>   	out	dx, ax
  7595                              <1>   	;mov	dx, 1CFh ; VBE_DISPI_IOPORT_DATA
  7596 000037A7 FEC2                <1>   	inc	dl
  7597 000037A9 66ED                <1> 	in	ax, dx
  7598 000037AB 50                  <1> 	push	eax
  7599 000037AC 66BAD403            <1> 	mov	dx, 3D4h ; VGAREG_VGA_CRTC_ADDRESS
  7600 000037B0 88C4                <1>   	mov	ah, al
  7601 000037B2 B012                <1> 	mov	al, 12h ; Vertical display end register
  7602 000037B4 66EF                <1>   	out	dx, ax
  7603 000037B6 58                  <1>   	pop	eax
  7604 000037B7 B007                <1>   	mov	al, 07h	; Overflow register
  7605 000037B9 EE                  <1>   	out	dx, al
  7606 000037BA 6642                <1>   	inc	dx
  7607 000037BC EC                  <1>   	in	al, dx ; read overflow register
  7608 000037BD 24BD                <1>   	and	al, 0BDh ; clear VDE 9th and 10th bits	
  7609 000037BF F6C401              <1>   	test	ah, 01h
  7610 000037C2 7402                <1>   	jz	short bit8_clear
  7611 000037C4 0C02                <1>   	or	al, 02h ; VDE 9th bit (bit 8) in bit 1
  7612                              <1> bit8_clear:
  7613 000037C6 F6C402              <1>   	test	ah, 02h
  7614 000037C9 7402                <1>   	jz	short bit9_clear
  7615 000037CB 0C40                <1>   	or	al, 40h ; VDE 10th bit (bit 9) in bit 6
  7616                              <1> bit9_clear:
  7617 000037CD EE                  <1>   	out	dx, al
  7618                              <1> 
  7619                              <1>   	; other settings
  7620 000037CE 66BAD403            <1>  	mov	dx, 3D4h ; VGAREG_VGA_CRTC_ADDRESS
  7621 000037D2 66B80900            <1>   	mov	ax, 0009h ; Maximum scan line register
  7622 000037D6 66EF                <1>   	out	dx, ax	; Reset
  7623 000037D8 B017                <1>   	mov	al, 17h ; Mode control register		
  7624 000037DA EE                  <1>   	out	dx, al
  7625                              <1>  	;mov	dx, 3D5h ; VGAREG_VGA_CRTC_DATA
  7626 000037DB FEC2                <1>   	inc	dl
  7627 000037DD EC                  <1> 	in	al, dx	; Read mode control register
  7628 000037DE 0C03                <1>   	or	al, 03h ; Set SRS and CMS bits
  7629 000037E0 EE                  <1>   	out	dx, al 
  7630 000037E1 66BADA03            <1>   	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  7631 000037E5 EC                  <1>   	in	al, dx	 ; clear flip-flop
  7632 000037E6 66BAC003            <1>   	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  7633 000037EA B010                <1>   	mov	al, 10h	; Mode control register
  7634 000037EC EE                  <1>   	out	dx, al
  7635                              <1> 	;mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  7636 000037ED FEC2                <1> 	inc	dl
  7637 000037EF EC                  <1> 	in	al, dx
  7638 000037F0 0C01                <1> 	or	al, 01h ; select graphics mode
  7639                              <1> 	;mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  7640 000037F2 FECA                <1> 	dec	dl
  7641 000037F4 EE                  <1> 	out	dx, al ; Write to mode control register
  7642 000037F5 B020                <1> 	mov	al, 20h ; Palette RAM <-> display memory
  7643 000037F7 EE                  <1> 	out	dx, al ; Write to attribute addr register
  7644 000037F8 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  7645 000037FC 66B80605            <1> 	mov	ax, 0506h ; Misc. register, graph, mm 1
  7646 00003800 66EF                <1> 	out	dx, ax
  7647 00003802 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  7648 00003806 66B8020F            <1> 	mov	ax, 0F02h ; Map mask register, all planes
  7649 0000380A 66EF                <1> 	out	dx, ax
  7650                              <1> 
  7651                              <1>   	; settings for >= 8bpp
  7652                              <1> 
  7653                              <1> 	;mov	dx, 1CEh ; VBE_DISPI_IOPORT_INDEX
  7654                              <1> 	;mov	ax, 03h ; VBE_DISPI_INDEX_BPP
  7655                              <1> 	;out	dx, ax
  7656                              <1> 	;;mov	dx, 1CFh ; VBE_DISPI_IOPORT_DATA
  7657                              <1> 	;inc	dl
  7658                              <1> 	;in	ax, dx
  7659                              <1> 	;cmp	al, 08h  ; < 8 bits per pixel
  7660                              <1> 	;jb	short vga_compat_end
  7661                              <1> 
  7662 0000380C 66BAD403            <1> 	mov	dx, 3D4h ; VGAREG_VGA_CRTC_ADDRESS
  7663 00003810 B014                <1> 	mov	al, 14h  ; Underline location register
  7664 00003812 EE                  <1> 	out	dx, al
  7665                              <1> 	;mov	dx, 3D5h ; VGAREG_VGA_CRTC_DATA
  7666 00003813 FEC2                <1> 	inc	dl
  7667 00003815 EC                  <1> 	in	al, dx	
  7668 00003816 0C40                <1> 	or	al, 40h	 ; enable double word mode
  7669 00003818 EE                  <1> 	out	dx, al
  7670 00003819 66BADA03            <1> 	mov	dx, 3DAh ; VGAREG_ACTL_RESET
  7671 0000381D EC                  <1> 	in	al, dx	 ; clear flip-flop
  7672 0000381E 66BAC003            <1> 	mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  7673 00003822 B010                <1> 	mov	al, 10h	 ; Mode control register
  7674 00003824 EE                  <1> 	out	dx, al
  7675                              <1> 	;mov	dx, 3C1h ; VGAREG_ACTL_READ_DATA
  7676 00003825 FEC2                <1> 	inc	dl
  7677 00003827 EC                  <1> 	in	al, dx
  7678 00003828 0C40                <1> 	or	al, 40h  ; Pixel clock select is 1 	
  7679                              <1> 	;mov	dx, 3C0h ; VGAREG_ACTL_ADDRESS
  7680 0000382A FECA                <1> 	dec	dl
  7681 0000382C EE                  <1> 	out	dx, al	 ; update mode control reggister
  7682 0000382D B020                <1> 	mov	al, 20h	 ; select display memory as PAS	
  7683 0000382F EE                  <1> 	out	dx, al
  7684 00003830 66BAC403            <1> 	mov	dx, 3C4h ; VGAREG_SEQU_ADDRESS
  7685 00003834 B004                <1> 	mov	al, 04h	; Memory mode register
  7686 00003836 EE                  <1> 	out	dx, al
  7687                              <1> 	;mov	dx, 3C5h ; VGAREG_SEQU_DATA
  7688 00003837 FEC2                <1> 	inc	dl
  7689 00003839 EC                  <1> 	in	al, dx
  7690 0000383A 0C08                <1> 	or	al, 08h	; enable chain four
  7691 0000383C EE                  <1> 	out	dx, al
  7692 0000383D 66BACE03            <1> 	mov	dx, 3CEh ; VGAREG_GRDC_ADDRESS
  7693 00003841 B005                <1> 	mov	al, 05h	 ; Mode register	
  7694 00003843 EE                  <1> 	out	dx, al
  7695                              <1> 	;mov	dx, 3CFh ; VGAREG_GRDC_DATA
  7696 00003844 FEC2                <1> 	inc	dl
  7697 00003846 EC                  <1> 	in	al, dx	
  7698 00003847 249F                <1> 	and	al, 9Fh	 ; clear shift register 
  7699 00003849 0C40                <1> 	or	al, 40h  ; set shift register to 2
  7700 0000384B EE                  <1> 	out	dx, al
  7701                              <1> 
  7702                              <1> vga_compat_end:
  7703                              <1>   	;pop	edx
  7704                              <1>   	;pop	eax
  7705 0000384C C3                  <1> 	retn
  7706                              <1> 
  7707                              <1> vga_set_virt_width:
  7708                              <1> 	; 27/11/2020
  7709                              <1> 	; 25/11/2020
  7710                              <1> 	; (vbe.c, 02/01/2020, vruppert)
  7711                              <1> 	;
  7712                              <1> 	; Input:
  7713                              <1> 	;	AX = resolution (screen width)
  7714                              <1> 	;
  7715                              <1> 	; Modified registers: eax, edx
  7716                              <1> 
  7717                              <1>   	;;push	ebx
  7718                              <1>   	;push	edx
  7719                              <1> 	;push	eax
  7720                              <1>   	;mov	ebx, eax
  7721                              <1>   	;call	dispi_get_bpp ; bits per pixel
  7722                              <1> 	;cmp	al, 4
  7723                              <1> 	;ja	short set_width_svga  ; 8, 16, 24, 32 
  7724                              <1> 	;shr	bx, 1
  7725                              <1> ;set_width_svga:
  7726                              <1> 	;shr	bx, 3
  7727                              <1> 	;mov	eax, [esp]
  7728 0000384D 66C1E803            <1> 	shr	ax, 3	; / 8, bytes per row
  7729 00003851 66BAD403            <1> 	mov	dx, 3D4h ; VGAREG_VGA_CRTC_ADDRESS
  7730                              <1> 	;mov	ah, bl	; 
  7731 00003855 88C4                <1> 	mov	ah, al	; width in bytes
  7732 00003857 B013                <1> 	mov	al, 13h	; offset register
  7733 00003859 66EF                <1> 	out	dx, ax	; index (3D4h) and data (3D5h)
  7734                              <1> 	;pop	eax
  7735                              <1> 	;pop  	edx
  7736                              <1> 	;;pop	ebx
  7737 0000385B C3                  <1> 	retn
  7738                              <1> 
  7739                              <1> ; 24/11/2020
  7740                              <1> 
  7741                              <1> struc bmi ; BOCHS/PLEX86 MODE INFO structure/table 
  7742 00000000 <res 00000002>      <1>  .mode:	  resw 1
  7743 00000002 <res 00000002>      <1>  .width:  resw 1
  7744 00000004 <res 00000002>      <1>  .height: resw 1
  7745 00000006 <res 00000002>      <1>  .depth:  resw 1
  7746                              <1>  .size:	
  7747                              <1> endstruc
  7748                              <1> 
  7749                              <1> struc MODEINFO
  7750 00000000 <res 00000002>      <1>  .mode:			resw 1  ; 1XXh
  7751 00000002 <res 00000002>      <1>  .ModeAttributes:	resw 1
  7752 00000004 <res 00000001>      <1>  .WinAAttributes:	resb 1
  7753 00000005 <res 00000001>      <1>  .WinBAttributes:	resb 1	; = 0
  7754 00000006 <res 00000002>      <1>  .WinGranularity:	resw 1
  7755 00000008 <res 00000002>      <1>  .WinSize:		resw 1
  7756 0000000A <res 00000002>      <1>  .WinASegment:		resw 1
  7757 0000000C <res 00000002>      <1>  .WinBSegment:		resw 1	; = 0
  7758 0000000E <res 00000004>      <1>  .WinFuncPtr:		resd 1	; = 0
  7759 00000012 <res 00000002>      <1>  .BytesPerScanLine:	resw 1
  7760 00000014 <res 00000002>      <1>  .XResolution:		resw 1
  7761 00000016 <res 00000002>      <1>  .YResolution:		resw 1
  7762 00000018 <res 00000001>      <1>  .XCharSize:		resb 1
  7763 00000019 <res 00000001>      <1>  .YCharSize:		resb 1
  7764 0000001A <res 00000001>      <1>  .NumberOfPlanes: 	resb 1
  7765 0000001B <res 00000001>      <1>  .BitsPerPixel:		resb 1
  7766 0000001C <res 00000001>      <1>  .NumberOfBanks:	resb 1
  7767 0000001D <res 00000001>      <1>  .MemoryModel:		resb 1
  7768 0000001E <res 00000001>      <1>  .BankSize:		resb 1	; = 0
  7769 0000001F <res 00000001>      <1>  .NumberOfImagePages: 	resb 1
  7770 00000020 <res 00000001>      <1>  .Reserved_page:	resb 1	; = 0
  7771 00000021 <res 00000001>      <1>  .RedMaskSize:		resb 1
  7772 00000022 <res 00000001>      <1>  .RedFieldPosition: 	resb 1
  7773 00000023 <res 00000001>      <1>  .GreenMaskSize:	resb 1
  7774 00000024 <res 00000001>      <1>  .GreenFieldPosition: 	resb 1
  7775 00000025 <res 00000001>      <1>  .BlueMaskSize:		resb 1
  7776 00000026 <res 00000001>      <1>  .BlueFieldPosition: 	resb 1
  7777 00000027 <res 00000001>      <1>  .RsvdMaskSize:		resb 1
  7778 00000028 <res 00000001>      <1>  .RsvdFieldPosition: 	resb 1
  7779 00000029 <res 00000001>      <1>  .DirectColorModeInfo: 	resb 1
  7780 0000002A <res 00000004>      <1>  .PhysBasePtr:		resd 1
  7781 0000002E <res 00000004>      <1>  .OffScreenMemOffset: 	resd 1	; = 0
  7782 00000032 <res 00000002>      <1>  .OffScreenMemSize: 	resw 1	; = 0
  7783 00000034 <res 00000002>      <1>  .LinBytesPerScanLine: 	resw 1
  7784 00000036 <res 00000001>      <1>  .BnkNumberOfPages: 	resb 1
  7785 00000037 <res 00000001>      <1>  .LinNumberOfPages: 	resb 1
  7786 00000038 <res 00000001>      <1>  .LinRedMaskSize:	resb 1
  7787 00000039 <res 00000001>      <1>  .LinRedFieldPosition1: resb 1
  7788 0000003A <res 00000001>      <1>  .LinGreenMaskSize1: 	resb 1
  7789 0000003B <res 00000001>      <1>  .LinGreenFieldPosition:resb 1
  7790 0000003C <res 00000001>      <1>  .LinBlueMaskSize: 	resb 1
  7791 0000003D <res 00000001>      <1>  .LinBlueFieldPosition:	resb 1
  7792 0000003E <res 00000001>      <1>  .LinRsvdMaskSize: 	resb 1
  7793 0000003F <res 00000001>      <1>  .LinRsvdFieldPosition:	resb 1
  7794 00000040 <res 00000004>      <1>  .MaxPixelClock:	resd 1	; = 0
  7795                              <1> .size:
  7796                              <1> endstruc
  7797                              <1> 
  7798                              <1> set_mode_info_list:
  7799                              <1> 	; 24/11/2020
  7800                              <1> 	; (vbetables-gen.c)
  7801                              <1> 	; Input:
  7802                              <1> 	;   BX = VBE mode (including bochs special modes) 
  7803                              <1> 	; Output:
  7804                              <1> 	;	EAX = MODE_INFO_LIST address
  7805                              <1> 	;	(if mode is not found, EAX = 0)
  7806                              <1> 	;
  7807                              <1> 	; Modified registes: eax, ebx, ecx, edx, esi, edi 
  7808                              <1> 
  7809 0000385C BE[066A0000]        <1> 	mov	esi, b_vbe_modes ; bochs mode info base table	
  7810 00003861 BF[A4110300]        <1> 	mov	edi, MODE_INFO_LIST ; mode info list (4F01h)
  7811                              <1> sml_0:
  7812 00003866 66AD                <1> 	lodsw	
  7813 00003868 6639D8              <1> 	cmp	ax, bx ; is mode number same ?
  7814 0000386B 740E                <1> 	je	short sml_1 ; yes
  7815 0000386D AD                  <1> 	lodsd
  7816 0000386E 66AD                <1> 	lodsw	
  7817 00003870 81FE[C66A0000]      <1> 	cmp	esi, end_of_b_vbe_modes
  7818 00003876 72EE                <1> 	jb	short sml_0
  7819                              <1> 	; not found
  7820 00003878 31C0                <1> 	xor	eax, eax ; 0
  7821 0000387A C3                  <1> 	retn
  7822                              <1> sml_1:
  7823 0000387B 66AB                <1> 	stosw	; mode
  7824 0000387D AD                  <1> 	lodsd	; width, height
  7825 0000387E 89C2                <1> 	mov	edx, eax
  7826 00003880 50                  <1> 	push	eax ; ***
  7827 00003881 66AD                <1> 	lodsw	; depth
  7828 00003883 50                  <1> 	push	eax ; **
  7829                              <1> 
  7830                              <1> 	;add	al, 7 ; only for 15 bit colors (not used here)
  7831 00003884 C0E803              <1> 	shr	al, 3 ; / 8
  7832 00003887 66F7E2              <1> 	mul	dx  ; pitch = width * ((depth+7)/8)
  7833                              <1> 		; ax = pitch
  7834 0000388A 50                  <1> 	push	eax ; *
  7835 0000388B C1EA10              <1> 	shr	edx, 16
  7836 0000388E 66F7E2              <1> 	mul	dx ; height * pitch
  7837 00003891 0FB7C8              <1> 	movzx	ecx, ax						 
  7838 00003894 B800000001          <1> 	mov	eax, VBE_DISPI_TOTAL_VIDEO_MEMORY_MB * 1024 * 1024
  7839 00003899 31D2                <1> 	xor	edx, edx			
  7840 0000389B F7F1                <1> 	div	ecx
  7841                              <1> 		; eax = pages = vram_size / (height*pitch)
  7842                              <1> 	
  7843 0000389D 89C1                <1> 	mov	ecx, eax ; pages 
  7844                              <1> 		
  7845 0000389F 66B89B00            <1> 	mov	ax, MODE_ATTRIBUTES
  7846 000038A3 66AB                <1> 	stosw	; ModeAttributes
  7847 000038A5 B007                <1> 	mov	al, WINA_ATTRIBUTES
  7848 000038A7 AA                  <1> 	stosb	; WinAAttributes
  7849 000038A8 30C0                <1> 	xor	al, al ; WinBAttributes = 0
  7850 000038AA AA                  <1> 	stosb
  7851 000038AB 66B84000            <1> 	mov	ax, VBE_DISPI_BANK_SIZE_KB
  7852 000038AF 66AB                <1> 	stosw	; WinGranularity
  7853 000038B1 66AB                <1> 	stosw	; WinSize
  7854 000038B3 66B800A0            <1> 	mov	ax, VGAMEM_GRAPH
  7855 000038B7 66AB                <1> 	stosw	; WinASegment
  7856 000038B9 29C0                <1> 	sub	eax, eax
  7857 000038BB 66AB                <1> 	stosw	; WinBSegment = 0
  7858 000038BD AB                  <1> 	stosd	; WinFuncPtr = 0
  7859                              <1> 
  7860 000038BE 58                  <1> 	pop	eax ; * ; pitch
  7861 000038BF 89C3                <1> 	mov	ebx, eax  
  7862 000038C1 66AB                <1> 	stosw	; BytesPerScanLine
  7863                              <1> 
  7864 000038C3 5A                  <1> 	pop	edx ; ** ; depth (bits per pixel)
  7865 000038C4 58                  <1> 	pop	eax ; *** width, height
  7866                              <1> 
  7867                              <1>  	; // Mandatory information for VBE 1.2 and above
  7868                              <1> 
  7869 000038C5 66AB                <1> 	stosw	; XResolution (width)
  7870 000038C7 C1E810              <1> 	shr	eax, 16
  7871 000038CA 50                  <1> 	push	eax ; **** height
  7872 000038CB 66AB                <1> 	stosw	; YResolution (height)
  7873 000038CD B008                <1> 	mov	al, 8
  7874 000038CF AA                  <1>  	stosb	; XCharSize  ; char width
  7875 000038D0 B010                <1> 	mov	al, 16
  7876 000038D2 AA                  <1> 	stosb	; YCharSize  ; char height
  7877 000038D3 B001                <1> 	mov	al, 1
  7878 000038D5 AA                  <1> 	stosb	; NumberOfPlanes
  7879                              <1> 	;movzx	eax, dl
  7880 000038D6 6689D0              <1> 	mov	ax, dx ; eax <= 32
  7881 000038D9 AA                  <1> 	stosb	; BitsPerPixel
  7882                              <1> 	; Number of banks = (height * pitch + 65535) / 65536
  7883                              <1> 	;pop	eax ; ****
  7884                              <1> 	;push	edx ; *****
  7885 000038DA 870424              <1> 	xchg	eax, [esp] ; *****	
  7886 000038DD F7E3                <1> 	mul	ebx  ; pitch (ebx) * height (eax)
  7887 000038DF 05FFFF0000          <1> 	add	eax, 65535
  7888 000038E4 C1E810              <1> 	shr	eax, 16 ; / 65536
  7889 000038E7 AA                  <1> 	stosb	; NumberOfBanks
  7890 000038E8 80FA08              <1> 	cmp	dl, 8 ; 8 bits per pixel
  7891 000038EB 7604                <1> 	jna	short sml_2
  7892 000038ED B004                <1> 	mov	al, VBE_MEMORYMODEL_PACKED_PIXEL
  7893 000038EF EB02                <1> 	jmp	short sml_3
  7894                              <1> sml_2:
  7895                              <1> 	; 16, 24, 32 bts per pixel
  7896 000038F1 B006                <1> 	mov	al, VBE_MEMORYMODEL_DIRECT_COLOR	
  7897                              <1> sml_3:
  7898 000038F3 AA                  <1> 	stosb
  7899 000038F4 30C0                <1> 	xor	al, al ; 0
  7900 000038F6 AA                  <1> 	stosb	; BankSize = 0
  7901 000038F7 49                  <1> 	dec	ecx ; pages - 1
  7902                              <1> 	; NumberOfImagePages = 262 for 320x200x8 mode
  7903 000038F8 66B8FF00            <1> 	mov	ax, 255
  7904 000038FC 6639C1              <1> 	cmp	cx, ax
  7905 000038FF 7302                <1> 	jnb	short sml_4
  7906 00003901 88C8                <1> 	mov	al, cl	 
  7907                              <1> sml_4:
  7908 00003903 AA                  <1> 	stosb	; NumberOfImagePages (1 byte)
  7909 00003904 28C0                <1> 	sub	al, al
  7910 00003906 AA                  <1> 	stosb	; Reserved_page = 0
  7911 00003907 58                  <1> 	pop	eax ; ***** ; depth
  7912 00003908 88C1                <1> 	mov	cl, al
  7913                              <1> 	; eax < = 32
  7914 0000390A 2C08                <1> 	sub	al, 8 ; 8->0, 16->8, 24->16, 32->24	
  7915 0000390C BE[C66A0000]        <1> 	mov	esi, direct_color_fields
  7916 00003911 01C6                <1> 	add	esi, eax
  7917 00003913 56                  <1> 	push	esi ; ******
  7918 00003914 AD                  <1> 	lodsd	; RedMaskSize (AL), RedFieldPosition (AH)
  7919                              <1> 	     	; GreenMaskSize (16), GreenFieldPosition (24)	
  7920 00003915 AB                  <1> 	stosd
  7921 00003916 AD                  <1> 	lodsd	; BlueMaskSize (AL), BlueFieldPosition (AH)
  7922                              <1> 	     	; RsvdMaskSize (16), RsvdFieldPosition (24)
  7923 00003917 AB                  <1> 	stosd
  7924 00003918 5E                  <1> 	pop	esi ; ******
  7925                              <1> 
  7926 00003919 30C0                <1> 	xor	al, al ; 0
  7927 0000391B 80F920              <1> 	cmp	cl, 32
  7928 0000391E 72E3                <1> 	jb	short sml_4
  7929 00003920 B002                <1> 	mov	al, VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  7930                              <1> sml_5: 
  7931 00003922 AA                  <1> 	stosb	; DirectColorModeInfo
  7932                              <1> 
  7933                              <1> 	; // Mandatory information for VBE 2.0 and above
  7934                              <1> 
  7935 00003923 B8000000E0          <1> 	mov	eax, VBE_DISPI_LFB_PHYSICAL_ADDRESS
  7936 00003928 AB                  <1> 	stosd	; PhysBasePtr
  7937 00003929 29C0                <1> 	sub	eax, eax
  7938 0000392B AB                  <1> 	stosd	; OffScreenMemOffset = 0
  7939 0000392C 66AB                <1> 	stosw	; OffScreenMemSize = 0
  7940                              <1> 
  7941                              <1> 	;// Mandatory information for VBE 3.0 and above
  7942                              <1> 
  7943                              <1> 	; ebx = pitch
  7944 0000392E 6689D8              <1> 	mov	ax, bx
  7945                              <1> 	;stosw
  7946                              <1> 
  7947                              <1> 	;xor	al, al
  7948                              <1>      	;stosb	; BnkNumberOfPages = 0
  7949                              <1>      	;stosb	; LinNumberOfPages = 0
  7950                              <1> 
  7951 00003931 AB                  <1> 	stosd	; pitch (word), 0 (byte), 0 (byte)  
  7952                              <1> 
  7953 00003932 AD                  <1> 	lodsd	; LinRedMaskSize (AL), LinRedFieldPosition (AH)
  7954                              <1> 	     	; LinGreenMaskSize (16), LinGreenFieldPosition (24)	
  7955 00003933 AB                  <1> 	stosd
  7956 00003934 AD                  <1> 	lodsd	; LinBlueMaskSize (AL), LinBlueFieldPosition (AH)
  7957                              <1> 	     	; LinRsvdMaskSize (16), LinRsvdFieldPosition (24)
  7958 00003935 AB                  <1> 	stosd
  7959                              <1> 
  7960 00003936 29C0                <1> 	sub	eax, eax
  7961 00003938 AB                  <1> 	stosd	; MaxPixelClock = 0
  7962                              <1> 
  7963 00003939 B8[A4110300]        <1> 	mov	eax, MODE_INFO_LIST
  7964 0000393E C3                  <1> 	retn	
  7965                              <1> 
  7966                              <1> ; end of set_mode_info_list ; edi = set_mode_info_list + 68
  7967                              <1> 
  7968                              <1> %endif
  7969                              <1> 
  7970                              <1> ; -----------
  7971                              <1> 
  7972                              <1> %if 0
  7973                              <1> 
  7974                              <1> mode_info_find_mode:
  7975                              <1> 	; 25/11/2020
  7976                              <1> 	; Input:
  7977                              <1> 	;	bx = VESA VBE2 video mode (+ bochs extensions)
  7978                              <1> 	; Output:
  7979                              <1> 	;	esi = mode info address (for BX input)
  7980                              <1> 	;	esi = 0 -> not found
  7981                              <1> 	;
  7982                              <1> 	; Modified registers: eax, esi
  7983                              <1> 
  7984                              <1> 	xor	eax, eax
  7985                              <1> 	mov	esi, MODE_INFO_LIST
  7986                              <1> mifm_1:
  7987                              <1> 	mov	ax, [esi]
  7988                              <1> 	cmp	ax, bx
  7989                              <1> 	je	short mifm_2
  7990                              <1> 	add	esi, MODEINFO.size ; add esi, 68
  7991                              <1> 	cmp	esi, VBE_VESA_MODE_END_OF_LIST
  7992                              <1> 	jb	short mifm_1
  7993                              <1> 	; not found
  7994                              <1> 	sub	esi, esi ; 0
  7995                              <1> mifm_2
  7996                              <1> 	retn
  7997                              <1> 
  7998                              <1> dispi_get_bpp:
  7999                              <1> 	; 28/11/2020
  8000                              <1> 	; Input:
  8001                              <1> 	;	none
  8002                              <1> 	; Output:
  8003                              <1> 	;	al = Bits per pixel
  8004                              <1> 	;	     (8,16,24,32)
  8005                              <1> 	;	ah = Bytes per pixel
  8006                              <1> 	;	     (1,2,3,4)	
  8007                              <1> 	;
  8008                              <1> 	; Modified registers: none
  8009                              <1> 
  8010                              <1> 	;push	edx
  8011                              <1> 	;mov	dx, 01CEh ; VBE_DISPI_IOPORT_INDEX
  8012                              <1> 	;mov	ax, 03h	  ; VBE_DISPI_INDEX_BPP
  8013                              <1> 	;out	dx, ax
  8014                              <1> 	;;mov	dx, 01CFh ; VBE_DISPI_IOPORT_DATA
  8015                              <1> 	;;mov	dl, 0CFh
  8016                              <1> 	;inc	dl
  8017                              <1> 	;in	ax, dx
  8018                              <1> 	;mov	ah, al
  8019                              <1> 	;shr	ah, 3 ; / 8
  8020                              <1> 	;;test	al, 7 ; 15 bit graphips mode
  8021                              <1>  	;;jz	short get_bpp_noinc
  8022                              <1> 	;;inc	ah
  8023                              <1> ;;get_bpp_noinc:
  8024                              <1> 	;pop	edx
  8025                              <1> 	;retn
  8026                              <1> 
  8027                              <1> 	; 28/11/2020
  8028                              <1> 	; Modified registers: edx
  8029                              <1> 	;push	edx
  8030                              <1> 	mov	dx, 03h ; VBE_DISPI_INDEX_BPP
  8031                              <1> 	call	dispi_get_parms
  8032                              <1> 	;pop	edx
  8033                              <1> 	;retn
  8034                              <1> 	mov	ah, al
  8035                              <1> 	shr	ah, 3 ; / 8
  8036                              <1> 	;test	al, 7 ; 15 bit graphips mode
  8037                              <1>  	;jz	short get_bpp_noinc
  8038                              <1> 	;inc	ah
  8039                              <1> ;get_bpp_noinc:
  8040                              <1> 	;pop	edx
  8041                              <1> 	retn
  8042                              <1> 
  8043                              <1> %endif
  8044                              <1> 
  8045                              <1> ; % include 'vidata.s' ; VIDEO DATA
  8046                              <1> 
  8047                              <1> ; /// End Of VIDEO FUNCTIONS ///
  2458                                  
  2459                                  setup_rtc_int:
  2460                                  ; source: http://wiki.osdev.org/RTC
  2461 0000393F FA                      	cli		; disable interrupts
  2462                                  	; default int frequency is 1024 Hz (Lower 4 bits of register A is 0110b or 6)
  2463                                  	; in order to change this ...
  2464                                  	; frequency  = 32768 >> (rate-1) --> 32768 >> 5 = 1024
  2465                                  	; (rate must be above 2 and not over 15)
  2466                                  	; new rate = 15 --> 32768 >> (15-1) = 2 Hz
  2467 00003940 B08A                    	mov	al, 8Ah 
  2468 00003942 E670                    	out	70h, al ; set index to register A, disable NMI
  2469 00003944 90                      	nop
  2470 00003945 E471                    	in	al, 71h ; get initial value of register A
  2471 00003947 88C4                    	mov 	ah, al
  2472 00003949 80E4F0                  	and	ah, 0F0h
  2473 0000394C B08A                    	mov	al, 8Ah 
  2474 0000394E E670                    	out	70h, al ; reset index to register A
  2475 00003950 88E0                    	mov	al, ah
  2476 00003952 0C0F                    	or	al, 0Fh	; new rate (0Fh -> 15)
  2477 00003954 E671                    	out	71h, al ; write only our rate to A. Note, rate is the bottom 4 bits. 
  2478                                  	; enable RTC interrupt
  2479 00003956 B08B                    	mov	al, 8Bh ;
  2480 00003958 E670                    	out	70h, al ; select register B and disable NMI
  2481 0000395A 90                      	nop
  2482 0000395B E471                    	in	al, 71h ; read the current value of register B
  2483 0000395D 88C4                    	mov	ah, al  ;
  2484 0000395F B08B                    	mov 	al, 8Bh ;
  2485 00003961 E670                    	out	70h, al ; set the index again (a read will reset the index to register B)	
  2486 00003963 88E0                    	mov	al, ah  ;
  2487 00003965 0C40                    	or	al, 40h ;
  2488 00003967 E671                    	out	71h, al ; write the previous value ORed with 0x40. This turns on bit 6 of register B
  2489 00003969 FB                      	sti
  2490 0000396A C3                      	retn
  2491                                  
  2492                                  ; Write memory information
  2493                                  ; 29/01/2016
  2494                                  ; 06/11/2014
  2495                                  ; 14/08/2015 
  2496                                  memory_info:	
  2497 0000396B A1[845E0100]            	mov	eax, [memory_size] ; in pages
  2498 00003970 50                      	push	eax
  2499 00003971 C1E00C                  	shl	eax, 12		   ; in bytes
  2500 00003974 BB0A000000              	mov	ebx, 10
  2501 00003979 89D9                    	mov	ecx, ebx	   ; 10
  2502 0000397B BE[BD1E0100]            	mov	esi, mem_total_b_str	
  2503 00003980 E8BD000000              	call	bintdstr
  2504 00003985 58                      	pop	eax
  2505 00003986 B107                    	mov	cl, 7
  2506 00003988 BE[E11E0100]            	mov	esi, mem_total_p_str
  2507 0000398D E8B0000000              	call	bintdstr	
  2508                                  	; 14/08/2015
  2509 00003992 E8C8000000              	call	calc_free_mem
  2510                                  	; edx = calculated free pages
  2511                                  	; ecx = 0
  2512 00003997 A1[885E0100]            	mov 	eax, [free_pages]
  2513 0000399C 39D0                    	cmp	eax, edx ; calculated free mem value 
  2514                                  		; and initial free mem value are same or not?
  2515 0000399E 751D                    	jne 	short pmim ; print mem info with '?' if not
  2516 000039A0 52                      	push 	edx ; free memory in pages	
  2517                                  	;mov 	eax, edx
  2518 000039A1 C1E00C                  	shl	eax, 12 ; convert page count
  2519                                  			; to byte count
  2520 000039A4 B10A                    	mov	cl, 10
  2521 000039A6 BE[011F0100]            	mov	esi, free_mem_b_str
  2522 000039AB E892000000              	call	bintdstr
  2523 000039B0 58                      	pop	eax
  2524 000039B1 B107                    	mov	cl, 7
  2525 000039B3 BE[251F0100]            	mov	esi, free_mem_p_str
  2526 000039B8 E885000000              	call	bintdstr
  2527                                  pmim:
  2528 000039BD BE[AB1E0100]            	mov	esi, msg_memory_info
  2529                                  	;
  2530 000039C2 B407                    	mov	ah, 07h ; Black background, 
  2531                                  			; light gray forecolor
  2532                                  print_kmsg: ; 29/01/2016
  2533 000039C4 8825[AF5E0100]          	mov	[ccolor], ah
  2534                                  pkmsg_loop:
  2535 000039CA AC                      	lodsb
  2536 000039CB 08C0                    	or	al, al
  2537 000039CD 7410                    	jz	short pkmsg_ok
  2538 000039CF 56                      	push	esi
  2539                                  	; 13/05/2016
  2540 000039D0 0FB61D[AF5E0100]        	movzx	ebx, byte [ccolor]
  2541                                  			; Video page 0 (bh=0)
  2542 000039D7 E8F9E6FFFF              	call	_write_tty
  2543 000039DC 5E                      	pop	esi
  2544 000039DD EBEB                    	jmp	short pkmsg_loop
  2545                                  pkmsg_ok:
  2546 000039DF C3                      	retn
  2547                                  
  2548                                  ; Convert binary number to hexadecimal string
  2549                                  ; 10/05/2015  
  2550                                  ; dsectpm.s (28/02/2015)
  2551                                  ; Retro UNIX 386 v1 - Kernel v0.2.0.6  
  2552                                  ; 01/12/2014
  2553                                  ; 25/11/2014
  2554                                  ;
  2555                                  bytetohex:
  2556                                  	; INPUT ->
  2557                                  	; 	AL = byte (binary number)
  2558                                  	; OUTPUT ->
  2559                                  	;	AX = hexadecimal string
  2560                                  	;
  2561 000039E0 53                      	push	ebx
  2562 000039E1 31DB                    	xor	ebx, ebx
  2563 000039E3 88C3                    	mov	bl, al
  2564 000039E5 C0EB04                  	shr	bl, 4
  2565 000039E8 8A9B[323A0000]          	mov	bl, [ebx+hexchrs] 	 	
  2566 000039EE 86D8                    	xchg	bl, al
  2567 000039F0 80E30F                  	and	bl, 0Fh
  2568 000039F3 8AA3[323A0000]          	mov	ah, [ebx+hexchrs] 
  2569 000039F9 5B                      	pop	ebx	
  2570 000039FA C3                      	retn
  2571                                  
  2572                                  wordtohex:
  2573                                  	; INPUT ->
  2574                                  	; 	AX = word (binary number)
  2575                                  	; OUTPUT ->
  2576                                  	;	EAX = hexadecimal string
  2577                                  	;
  2578 000039FB 53                      	push	ebx
  2579 000039FC 31DB                    	xor	ebx, ebx
  2580 000039FE 86E0                    	xchg	ah, al
  2581 00003A00 6650                    	push	ax
  2582 00003A02 88E3                    	mov	bl, ah
  2583 00003A04 C0EB04                  	shr	bl, 4
  2584 00003A07 8A83[323A0000]          	mov	al, [ebx+hexchrs] 	 	
  2585 00003A0D 88E3                    	mov	bl, ah
  2586 00003A0F 80E30F                  	and	bl, 0Fh
  2587 00003A12 8AA3[323A0000]          	mov	ah, [ebx+hexchrs]
  2588 00003A18 C1E010                  	shl	eax, 16
  2589 00003A1B 6658                    	pop	ax
  2590 00003A1D 5B                      	pop	ebx
  2591 00003A1E EBC0                    	jmp	short bytetohex
  2592                                  	;mov	bl, al
  2593                                  	;shr	bl, 4
  2594                                  	;mov	bl, [ebx+hexchrs] 	 	
  2595                                  	;xchg	bl, al	 	
  2596                                  	;and	bl, 0Fh
  2597                                  	;mov	ah, [ebx+hexchrs] 
  2598                                  	;pop	ebx	
  2599                                  	;retn
  2600                                  
  2601                                  dwordtohex:
  2602                                  	; INPUT ->
  2603                                  	; 	EAX = dword (binary number)
  2604                                  	; OUTPUT ->
  2605                                  	;	EDX:EAX = hexadecimal string
  2606                                  	;
  2607 00003A20 50                      	push	eax
  2608 00003A21 C1E810                  	shr	eax, 16
  2609 00003A24 E8D2FFFFFF              	call	wordtohex
  2610 00003A29 89C2                    	mov	edx, eax
  2611 00003A2B 58                      	pop	eax
  2612 00003A2C E8CAFFFFFF              	call	wordtohex
  2613 00003A31 C3                      	retn
  2614                                  
  2615                                  ; 10/05/2015
  2616                                  hex_digits:
  2617                                  hexchrs:
  2618 00003A32 303132333435363738-     	db '0123456789ABCDEF'
  2618 00003A3B 39414243444546     
  2619                                  
  2620                                  ; Convert binary number to decimal/numeric string
  2621                                  ; 06/11/2014
  2622                                  ; Temporary Code
  2623                                  ;
  2624                                  
  2625                                  bintdstr:
  2626                                  	; EAX = binary number
  2627                                  	; ESI = decimal/numeric string address
  2628                                  	; EBX = divisor (10)
  2629                                  	; ECX = string length (<=10)
  2630 00003A42 01CE                    	add	esi, ecx
  2631                                  btdstr0:
  2632 00003A44 4E                      	dec	esi
  2633 00003A45 31D2                    	xor	edx, edx
  2634 00003A47 F7F3                    	div	ebx
  2635 00003A49 80C230                  	add	dl, 30h
  2636 00003A4C 8816                    	mov	[esi], dl
  2637 00003A4E FEC9                    	dec	cl
  2638 00003A50 740C                    	jz	short btdstr2 ; 08/09/2016
  2639 00003A52 09C0                    	or	eax, eax
  2640 00003A54 75EE                    	jnz	short btdstr0
  2641                                  btdstr1:
  2642 00003A56 4E                      	dec	esi
  2643 00003A57 C60620                          mov     byte [esi], 20h ; blank space
  2644 00003A5A FEC9                    	dec	cl
  2645 00003A5C 75F8                    	jnz	short btdstr1
  2646                                  btdstr2:
  2647 00003A5E C3                      	retn
  2648                                  
  2649                                  ; Calculate free memory pages on M.A.T.
  2650                                  ; 06/11/2014
  2651                                  ; Temporary Code
  2652                                  ;
  2653                                  
  2654                                  calc_free_mem:
  2655 00003A5F 31D2                    	xor	edx, edx
  2656                                  	;xor	ecx, ecx
  2657 00003A61 668B0D[985E0100]        	mov	cx, [mat_size] ; in pages
  2658 00003A68 C1E10A                  	shl	ecx, 10	; 1024 dwords per page
  2659 00003A6B BE00001000              	mov	esi, MEM_ALLOC_TBL
  2660                                  cfm0:
  2661 00003A70 AD                      	lodsd
  2662 00003A71 51                      	push	ecx
  2663 00003A72 B920000000              	mov	ecx, 32
  2664                                  cfm1:
  2665 00003A77 D1E8                    	shr	eax, 1
  2666 00003A79 7301                    	jnc	short cfm2
  2667 00003A7B 42                      	inc	edx
  2668                                  cfm2:
  2669 00003A7C E2F9                    	loop	cfm1
  2670 00003A7E 59                      	pop	ecx
  2671 00003A7F E2EF                    	loop	cfm0
  2672 00003A81 C3                      	retn
  2673                                  
  2674                                  %include 'diskio.s'  ; 07/03/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.2 - diskio.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 30/08/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; diskio.inc (22/08/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - DISKIO.INC
    20                              <1> ; Last Modification: 22/08/2015
    21                              <1> ; 	(Initialized Disk Parameters Data is in 'DISKDATA.INC') 
    22                              <1> ; 	(Uninitialized Disk Parameters Data is in 'DISKBSS.INC') 
    23                              <1> 
    24                              <1> ; DISK I/O SYSTEM - Erdogan Tan (Retro UNIX 386 v1 project)
    25                              <1> 
    26                              <1> ; ///////// DISK I/O SYSTEM ///////////////
    27                              <1> 
    28                              <1> ; 06/02/2015
    29                              <1> diskette_io:
    30 00003A82 F8                  <1> 	clc ; 20/07/2020
    31 00003A83 9C                  <1> 	pushfd
    32 00003A84 0E                  <1> 	push 	cs
    33 00003A85 E809000000          <1> 	call 	DISKETTE_IO_1
    34 00003A8A C3                  <1> 	retn
    35                              <1> 	
    36                              <1> ;;;;;; DISKETTE I/O ;;;;;;;;;;;;;;;;;;;; 06/02/2015 ;;;
    37                              <1> ;//////////////////////////////////////////////////////
    38                              <1> 
    39                              <1> ; DISKETTE I/O - Erdogan Tan (Retro UNIX 386 v1 project)
    40                              <1> ; 20/02/2015
    41                              <1> ; 06/02/2015 (unix386.s)
    42                              <1> ; 16/12/2014 - 02/01/2015 (dsectrm2.s)
    43                              <1> ;
    44                              <1> ; Code (DELAY) modifications - AWARD BIOS 1999 (ADISK.EQU, COMMON.MAC)
    45                              <1> ;
    46                              <1> ; ADISK.EQU
    47                              <1> 
    48                              <1> ;----- Wait control constants 
    49                              <1> 
    50                              <1> ;amount of time to wait while RESET is active.
    51                              <1> 
    52                              <1> WAITCPU_RESET_ON	EQU	21		;Reset on must last at least 14us
    53                              <1> 						;at 250 KBS xfer rate.
    54                              <1> 						;see INTEL MCS, 1985, pg. 5-456
    55                              <1> 
    56                              <1> WAITCPU_FOR_STATUS	EQU	100		;allow 30 microseconds for
    57                              <1> 						;status register to become valid
    58                              <1> 						;before re-reading.
    59                              <1> 
    60                              <1> ;After sending a byte to NEC, status register may remain
    61                              <1> ;incorrectly set for 24 us.
    62                              <1> 
    63                              <1> WAITCPU_RQM_LOW		EQU	24		;number of loops to check for
    64                              <1> 						;RQM low.
    65                              <1> 
    66                              <1> ; COMMON.MAC
    67                              <1> ;
    68                              <1> ;	Timing macros
    69                              <1> ;
    70                              <1> 
    71                              <1> %macro 		SIODELAY 0 			; SHORT IODELAY
    72                              <1> 		jmp short $+2
    73                              <1> %endmacro		
    74                              <1> 
    75                              <1> %macro		IODELAY  0			; NORMAL IODELAY
    76                              <1> 		jmp short $+2
    77                              <1> 		jmp short $+2
    78                              <1> %endmacro
    79                              <1> 
    80                              <1> %macro		NEWIODELAY 0
    81                              <1> 		out	0ebh,al
    82                              <1> %endmacro 
    83                              <1> 
    84                              <1> ; (According to) AWARD BIOS 1999 - ATORGS.ASM (dw -> equ, db -> equ)
    85                              <1> ;;; WAIT_FOR_MEM
    86                              <1> ;WAIT_FDU_INT_LO	equ	017798		; 2.5 secs in 30 micro units.
    87                              <1> ;WAIT_FDU_INT_HI	equ	1
    88                              <1> WAIT_FDU_INT_LH		equ	83334		; 27/02/2015 (2.5 seconds waiting)
    89                              <1> ;;; WAIT_FOR_PORT
    90                              <1> ;WAIT_FDU_SEND_LO	equ	16667		; .5 secons in 30 us units.
    91                              <1> ;WAIT_FDU_SEND_HI	equ	0
    92                              <1> WAIT_FDU_SEND_LH	equ 	16667		; 27/02/2015	
    93                              <1> ;Time to wait while waiting for each byte of NEC results = .5
    94                              <1> ;seconds.  .5 seconds = 500,000 micros.  500,000/30 = 16,667.
    95                              <1> ;WAIT_FDU_RESULTS_LO	equ	16667		; .5 seconds in 30 micro units.
    96                              <1> ;WAIT_FDU_RESULTS_HI	equ	0
    97                              <1> WAIT_FDU_RESULTS_LH	equ	16667  ; 27/02/2015
    98                              <1> ;;; WAIT_REFRESH
    99                              <1> ;amount of time to wait for head settle, per unit in parameter
   100                              <1> ;table = 1 ms.
   101                              <1> WAIT_FDU_HEAD_SETTLE	equ	33		; 1 ms in 30 micro units.
   102                              <1> 
   103                              <1> 
   104                              <1> ; //////////////// DISKETTE I/O ////////////////
   105                              <1> 
   106                              <1> ; 11/12/2014 (copy from IBM PC-XT Model 286 BIOS - POSTEQU.INC)
   107                              <1> 
   108                              <1> ;----------------------------------------
   109                              <1> ;	EQUATES USED BY POST AND BIOS	:
   110                              <1> ;----------------------------------------
   111                              <1> 
   112                              <1> ;--------- 8042 KEYBOARD INTERFACE AND DIAGNOSTIC CONTROL REGISTERS ------------
   113                              <1> ;PORT_A		EQU	060H		; 8042 KEYBOARD SCAN CODE/CONTROL PORT
   114                              <1> ;PORT_B		EQU	061H		; PORT B READ/WRITE DIAGNOSTIC REGISTER
   115                              <1> ;REFRESH_BIT	EQU	00010000B	; REFRESH TEST BIT
   116                              <1> 
   117                              <1> ;----------------------------------------
   118                              <1> ;	CMOS EQUATES FOR THIS SYSTEM	:
   119                              <1> ;-------------------------------------------------------------------------------
   120                              <1> ;CMOS_PORT	EQU	070H		; I/O ADDRESS OF CMOS ADDRESS PORT
   121                              <1> ;CMOS_DATA	EQU	071H		; I/O ADDRESS OF CMOS DATA PORT
   122                              <1> ;NMI		EQU	10000000B	; DISABLE NMI INTERRUPTS MASK -
   123                              <1> 					;  HIGH BIT OF CMOS LOCATION ADDRESS
   124                              <1> 
   125                              <1> ;---------- CMOS TABLE LOCATION ADDRESS'S ## -----------------------------------
   126                              <1> CMOS_DISKETTE	EQU	010H		; DISKETTE DRIVE TYPE BYTE	      ;
   127                              <1> ;		EQU	011H		; - RESERVED			      ;C
   128                              <1> CMOS_DISK	EQU	012H		; FIXED DISK TYPE BYTE		      ;H
   129                              <1> ;		EQU	013H		; - RESERVED			      ;E
   130                              <1> CMOS_EQUIP	EQU	014H		; EQUIPMENT WORD LOW BYTE	      ;C
   131                              <1> 
   132                              <1> ;---------- DISKETTE EQUATES ---------------------------------------------------
   133                              <1> INT_FLAG	EQU	10000000B	; INTERRUPT OCCURRENCE FLAG
   134                              <1> DSK_CHG 	EQU	10000000B	; DISKETTE CHANGE FLAG MASK BIT
   135                              <1> DETERMINED	EQU	00010000B	; SET STATE DETERMINED IN STATE BITS
   136                              <1> HOME		EQU	00010000B	; TRACK 0 MASK
   137                              <1> SENSE_DRV_ST	EQU	00000100B	; SENSE DRIVE STATUS COMMAND
   138                              <1> TRK_SLAP	EQU	030H		; CRASH STOP (48 TPI DRIVES)
   139                              <1> QUIET_SEEK	EQU	00AH		; SEEK TO TRACK 10
   140                              <1> ;MAX_DRV 	EQU	2		; MAX NUMBER OF DRIVES
   141                              <1> HD12_SETTLE	EQU	15		; 1.2 M HEAD SETTLE TIME
   142                              <1> HD320_SETTLE	EQU	20		; 320 K HEAD SETTLE TIME
   143                              <1> MOTOR_WAIT	EQU	37		; 2 SECONDS OF COUNTS FOR MOTOR TURN OFF
   144                              <1> 
   145                              <1> ;---------- DISKETTE ERRORS ----------------------------------------------------
   146                              <1> ;TIME_OUT	EQU	080H		; ATTACHMENT FAILED TO RESPOND
   147                              <1> ;BAD_SEEK	EQU	040H		; SEEK OPERATION FAILED
   148                              <1> BAD_NEC 	EQU	020H		; DISKETTE CONTROLLER HAS FAILED
   149                              <1> BAD_CRC 	EQU	010H		; BAD CRC ON DISKETTE READ
   150                              <1> MED_NOT_FND	EQU	00CH		; MEDIA TYPE NOT FOUND
   151                              <1> DMA_BOUNDARY	EQU	009H		; ATTEMPT TO DMA ACROSS 64K BOUNDARY
   152                              <1> BAD_DMA 	EQU	008H		; DMA OVERRUN ON OPERATION
   153                              <1> MEDIA_CHANGE	EQU	006H		; MEDIA REMOVED ON DUAL ATTACH CARD
   154                              <1> RECORD_NOT_FND	EQU	004H		; REQUESTED SECTOR NOT FOUND
   155                              <1> WRITE_PROTECT	EQU	003H		; WRITE ATTEMPTED ON WRITE PROTECT DISK
   156                              <1> BAD_ADDR_MARK	EQU	002H		; ADDRESS MARK NOT FOUND
   157                              <1> BAD_CMD 	EQU	001H		; BAD COMMAND PASSED TO DISKETTE I/O
   158                              <1> 
   159                              <1> ;---------- DISK CHANGE LINE EQUATES -------------------------------------------
   160                              <1> NOCHGLN 	EQU	001H		; NO DISK CHANGE LINE AVAILABLE
   161                              <1> CHGLN		EQU	002H		; DISK CHANGE LINE AVAILABLE
   162                              <1> 
   163                              <1> ;---------- MEDIA/DRIVE STATE INDICATORS ---------------------------------------
   164                              <1> TRK_CAPA	EQU	00000001B	; 80 TRACK CAPABILITY
   165                              <1> FMT_CAPA	EQU	00000010B	; MULTIPLE FORMAT CAPABILITY (1.2M)
   166                              <1> DRV_DET 	EQU	00000100B	; DRIVE DETERMINED
   167                              <1> MED_DET 	EQU	00010000B	; MEDIA DETERMINED BIT
   168                              <1> DBL_STEP	EQU	00100000B	; DOUBLE STEP BIT
   169                              <1> RATE_MSK	EQU	11000000B	; MASK FOR CLEARING ALL BUT RATE
   170                              <1> RATE_500	EQU	00000000B	; 500 KBS DATA RATE
   171                              <1> RATE_300	EQU	01000000B	; 300 KBS DATA RATE
   172                              <1> RATE_250	EQU	10000000B	; 250 KBS DATA RATE
   173                              <1> STRT_MSK	EQU	00001100B	; OPERATION START RATE MASK
   174                              <1> SEND_MSK	EQU	11000000B	; MASK FOR SEND RATE BITS
   175                              <1> 
   176                              <1> ;---------- MEDIA/DRIVE STATE INDICATORS COMPATIBILITY -------------------------
   177                              <1> M3D3U		EQU	00000000B	; 360 MEDIA/DRIVE NOT ESTABLISHED
   178                              <1> M3D1U		EQU	00000001B	; 360 MEDIA,1.2DRIVE NOT ESTABLISHED
   179                              <1> M1D1U		EQU	00000010B	; 1.2 MEDIA/DRIVE NOT ESTABLISHED
   180                              <1> MED_UNK 	EQU	00000111B	; NONE OF THE ABOVE
   181                              <1> 
   182                              <1> ;---------- INTERRUPT EQUATES --------------------------------------------------
   183                              <1> ;EOI		EQU	020H		; END OF INTERRUPT COMMAND TO 8259
   184                              <1> ;INTA00		EQU	020H		; 8259 PORT
   185                              <1> INTA01		EQU	021H		; 8259 PORT
   186                              <1> INTB00		EQU	0A0H		; 2ND 8259
   187                              <1> INTB01		EQU	0A1H		;
   188                              <1> 
   189                              <1> ;-------------------------------------------------------------------------------
   190                              <1> DMA08		EQU	008H		; DMA STATUS REGISTER PORT ADDRESS
   191                              <1> DMA		EQU	000H		; DMA CH.0 ADDRESS REGISTER PORT ADDRESS
   192                              <1> DMA18		EQU	0D0H		; 2ND DMA STATUS PORT ADDRESS
   193                              <1> DMA1		EQU	0C0H		; 2ND DMA CH.0 ADDRESS REGISTER ADDRESS
   194                              <1> ;-------------------------------------------------------------------------------
   195                              <1> ;TIMER		EQU	040H		; 8254 TIMER - BASE ADDRESS
   196                              <1> 
   197                              <1> ;-------------------------------------------------------------------------------
   198                              <1> DMA_PAGE	EQU	081H		; START OF DMA PAGE REGISTERS
   199                              <1> 
   200                              <1> ; 06/02/2015 (unix386.s, protected mode modifications)
   201                              <1> ; (unix386.s <-- dsectrm2.s)
   202                              <1> ; 11/12/2014 (copy from IBM PC-XT Model 286 BIOS - DSEG.INC)
   203                              <1> 
   204                              <1> ; 27/05/2016 - TRDOS 386 (TRDOS v2.0)
   205                              <1> ; 10/12/2014
   206                              <1> ;
   207                              <1> ;int40h:
   208                              <1> ;	pushf
   209                              <1> ;	push 	cs
   210                              <1> ;	;cli
   211                              <1> ;	call 	DISKETTE_IO_1
   212                              <1> ;	retn
   213                              <1> 
   214                              <1> ; DSKETTE ----- 04/21/86 DISKETTE BIOS
   215                              <1> ; (IBM PC XT Model 286 System BIOS Source Code, 04-21-86)
   216                              <1> ;
   217                              <1> 
   218                              <1> ;-- INT13H ---------------------------------------------------------------------
   219                              <1> ; DISKETTE I/O
   220                              <1> ;	THIS INTERFACE PROVIDES ACCESS TO THE 5 1/4 INCH 360 KB,
   221                              <1> ;	1.2 MB, 720 KB AND 1.44 MB DISKETTE DRIVES.
   222                              <1> ; INPUT
   223                              <1> ;	(AH) =  00H RESET DISKETTE SYSTEM
   224                              <1> ;		HARD RESET TO NEC, PREPARE COMMAND, RECALIBRATE REQUIRED
   225                              <1> ;		ON ALL DRIVES
   226                              <1> ;------------------------------------------------------------------------------- 
   227                              <1> ;	(AH)= 01H  READ THE STATUS OF THE SYSTEM INTO (AH)
   228                              <1> ;		@DISKETTE_STATUS FROM LAST OPERATION IS USED
   229                              <1> ;-------------------------------------------------------------------------------
   230                              <1> ;	REGISTERS FOR READ/WRITE/VERIFY/FORMAT
   231                              <1> ;	(DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHECKED)
   232                              <1> ;	(DH) - HEAD NUMBER (0-1 ALLOWED, NOT VALUE CHECKED)
   233                              <1> ;	(CH) - TRACK NUMBER (NOT VALUE CHECKED)
   234                              <1> ;		MEDIA	DRIVE	TRACK NUMBER
   235                              <1> ;		320/360	320/360	    0-39
   236                              <1> ;		320/360	1.2M	    0-39
   237                              <1> ;		1.2M	1.2M	    0-79
   238                              <1> ;		720K	720K	    0-79
   239                              <1> ;		1.44M	1.44M	    0-79	
   240                              <1> ;	(CL) - 	SECTOR NUMBER (NOT VALUE CHECKED, NOT USED FOR FORMAT)
   241                              <1> ;		MEDIA	DRIVE	SECTOR NUMBER
   242                              <1> ;		320/360	320/360	     1-8/9
   243                              <1> ;		320/360	1.2M	     1-8/9
   244                              <1> ;		1.2M	1.2M	     1-15
   245                              <1> ;		720K	720K	     1-9
   246                              <1> ;		1.44M	1.44M	     1-18		
   247                              <1> ;	(AL)	NUMBER OF SECTORS (NOT VALUE CHECKED)
   248                              <1> ;		MEDIA	DRIVE	MAX NUMBER OF SECTORS
   249                              <1> ;		320/360	320/360	        8/9
   250                              <1> ;		320/360	1.2M	        8/9
   251                              <1> ;		1.2M	1.2M		15
   252                              <1> ;		720K	720K		9
   253                              <1> ;		1.44M	1.44M		18
   254                              <1> ;
   255                              <1> ;	(ES:BX) - ADDRESS OF BUFFER (NOT REQUIRED FOR VERIFY)
   256                              <1> ;
   257                              <1> ;-------------------------------------------------------------------------------
   258                              <1> ;	(AH)= 02H  READ THE DESIRED SECTORS INTO MEMORY
   259                              <1> ;-------------------------------------------------------------------------------
   260                              <1> ;	(AH)= 03H  WRITE THE DESIRED SECTORS FROM MEMORY
   261                              <1> ;-------------------------------------------------------------------------------
   262                              <1> ;	(AH)= 04H  VERIFY THE DESIRED SECTORS
   263                              <1> ;-------------------------------------------------------------------------------
   264                              <1> ;	(AH)= 05H  FORMAT THE DESIRED TRACK
   265                              <1> ;		(ES,BX) MUST POINT TO THE COLLECTION OF DESIRED ADDRESS FIELDS
   266                              <1> ;		FOR THE	TRACK. EACH FIELD IS COMPOSED OF 4 BYTES, (C,H,R,N),
   267                              <1> ;		WHERE C = TRACK NUMBER, H=HEAD NUMBER, R = SECTOR NUMBER, 
   268                              <1> ;		N= NUMBER OF BYTES PER SECTOR (00=128,01=256,02=512,03=1024),
   269                              <1> ;		THERE MUST BE ONE ENTRY FOR EVERY SECTOR ON THE TRACK.
   270                              <1> ;		THIS INFORMATION IS USED TO FIND THE REQUESTED SECTOR DURING 
   271                              <1> ;		READ/WRITE ACCESS.
   272                              <1> ;		PRIOR TO FORMATTING A DISKETTE, IF THERE EXISTS MORE THAN
   273                              <1> ;		ONE SUPPORTED MEDIA FORMAT TYPE WITHIN THE DRIVE IN QUESTION,
   274                              <1> ;		THEN "SET DASD TYPE" (INT 13H, AH = 17H) OR 'SET MEDIA TYPE'
   275                              <1> ;		(INT 13H, AH =  18H) MUST BE CALLED TO SET THE DISKETTE TYPE
   276                              <1> ;		THAT IS TO BE FORMATTED. IF "SET DASD TYPE" OR "SET MEDIA TYPE"
   277                              <1> ;		IS NOT CALLED, THE FORMAT ROUTINE WILL ASSUME THE 
   278                              <1> ;		MEDIA FORMAT TO BE THE MAXIMUM CAPACITY OF THE DRIVE.
   279                              <1> ;
   280                              <1> ;		THESE PARAMETERS OF DISK BASE MUST BE CHANGED IN ORDER TO
   281                              <1> ;		FORMAT THE FOLLOWING MEDIAS:
   282                              <1> ;		---------------------------------------------
   283                              <1> ;		: MEDIA  :     DRIVE      : PARM 1 : PARM 2 :
   284                              <1> ;		---------------------------------------------
   285                              <1> ;		: 320K	 : 320K/360K/1.2M :  50H   :   8    :
   286                              <1> ;		: 360K	 : 320K/360K/1.2M :  50H   :   9    :
   287                              <1> ;		: 1.2M	 : 1.2M           :  54H   :  15    :
   288                              <1> ;		: 720K	 : 720K/1.44M     :  50H   :   9    :
   289                              <1> ;		: 1.44M	 : 1.44M          :  6CH   :  18    :		  	
   290                              <1> ;		---------------------------------------------
   291                              <1> ;		NOTES: - PARM 1 = GAP LENGTH FOR FORMAT
   292                              <1> ;		       - PARM 2 = EOT (LAST SECTOR ON TRACK)
   293                              <1> ;		       - DISK BASE IS POINTED BY DISK POINTER LOCATED
   294                              <1> ;			 AT ABSOLUTE ADDRESS 0:78.
   295                              <1> ;		       - WHEN FORMAT OPERATIONS ARE COMPLETE, THE PARAMETERS
   296                              <1> ;			 SHOULD BE RESTORED TO THEIR RESPECTIVE INITIAL VALUES.			
   297                              <1> ;-------------------------------------------------------------------------------
   298                              <1> ;	(AH) = 08H READ DRIVE PARAMETERS
   299                              <1> ;	REGISTERS
   300                              <1> ;	  INPUT
   301                              <1> ;	    (DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHECKED)
   302                              <1> ;	     ** 27/05/2016 - TRDOS 386 (TRDOS v2.0) **	
   303                              <1> ;            ** EBX = Buffer address for floppy disk parameters table **
   304                              <1> ;	  OUTPUT
   305                              <1> ;	    (ES:DI) POINTS TO DRIVE PARAMETER TABLE
   306                              <1> ; 	    *** TRDOS 386 note: floppy disk parameter table (16 bytes)
   307                              <1> ;	    will be returned to user in EBX, buffer address *** 27/05/2016 ***		
   308                              <1> ;					
   309                              <1> ;	    (CH) - LOW ORDER 8 OF 10 BITS MAXIMUM NUMBER OF TRACKS
   310                              <1> ;	    (CL) - BITS 7 & 6 - HIGH ORDER TWO BITS OF MAXIMUM TRACKS
   311                              <1> ;	           BITS 5 THRU 0 - MAXIMUM SECTORS PER TRACK
   312                              <1> ;	    (DH) - MAXIMUM HEAD NUMBER
   313                              <1> ;	    (DL) - NUMBER OF DISKETTE DRIVES INSTALLED
   314                              <1> ;	    (BH) - 0
   315                              <1> ;	    (BL) - BITS 7 THRU 4 - 0
   316                              <1> ;	           BITS 3 THRU 0 - VALID DRIVE TYPE VALUE IN CMOS
   317                              <1> ;	    (AX) - 0
   318                              <1> ;	 UNDER THE FOLLOWING CIRCUMSTANCES:
   319                              <1> ;	    (1) THE DRIVE NUMBER IS INVALID,
   320                              <1> ;	    (2) THE DRIVE TYPE IS UNKNOWN AND CMOS IS NOT PRESENT, 
   321                              <1> ;	    (3) THE DRIVE TYPE IS UNKNOWN AND CMOS IS BAD,
   322                              <1> ;	    (4) OR THE DRIVE TYPE IS UNKNOWN AND THE CMOS DRIVE TYPE IS INVALID
   323                              <1> ;	    THEN ES,AX,BX,CX,DH,DI=0 ; DL=NUMBER OF DRIVES. 
   324                              <1> ;	    IF NO DRIVES ARE PRESENT THEN: ES,AX,BX,CX,DX,DI=0.
   325                              <1> ;	    @DISKETTE_STATUS = 0 AND CY IS RESET.
   326                              <1> ;-------------------------------------------------------------------------------
   327                              <1> ;	(AH)= 15H  READ DASD TYPE
   328                              <1> ;	OUTPUT REGISTERS
   329                              <1> ;	(AH) - ON RETURN IF CARRY FLAG NOT SET, OTHERWISE ERROR	
   330                              <1> ;		00 - DRIVE NOT PRESENT	
   331                              <1> ;		01 - DISKETTE, NO CHANGE LINE AVAILABLE
   332                              <1> ;		02 - DISKETTE, CHANGE LINE AVAILABLE	
   333                              <1> ;		03 - RESERVED (FIXED DISK)
   334                              <1> ;	(DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHECKED)
   335                              <1> ;-------------------------------------------------------------------------------
   336                              <1> ;	(AH)= 16H  DISK CHANGE LINE STATUS
   337                              <1> ;	OUTPUT REGISTERS
   338                              <1> ;	(AH) - 00 - DISK CHANGE LINE NOT ACTIVE	
   339                              <1> ;	       06 - DISK CHANGE LINE ACTIVE & CARRY BIT ON
   340                              <1> ;	(DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHECKED)
   341                              <1> ;-------------------------------------------------------------------------------
   342                              <1> ;	(AH)= 17H  SET DASD TYPE FOR FORMAT
   343                              <1> ;	INPUT REGISTERS
   344                              <1> ;	(AL) -	00 - NOT USED	
   345                              <1> ;		01 - DISKETTE 320/360K IN 360K DRIVE	
   346                              <1> ;		02 - DISKETTE 360K IN 1.2M DRIVE
   347                              <1> ;		03 - DISKETTE 1.2M IN 1.2M DRIVE
   348                              <1> ;		04 - DISKETTE 720K IN 720K DRIVE
   349                              <1> ;	(DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHECKED:
   350                              <1> ;	       (DO NOT USE WHEN DISKETTE ATTACH CARD USED)
   351                              <1> ;-------------------------------------------------------------------------------
   352                              <1> ;	(AH)= 18H  SET MEDIA TYPE FOR FORMAT
   353                              <1> ;	INPUT REGISTERS
   354                              <1> ;	(CH) - LOW ORDER 8 OF 10 BITS MAXIMUM TRACKS
   355                              <1> ;	(CL) - BITS 7 & 6 - HIGH ORDER TWO BITS OF MAXIMUM TRACKS
   356                              <1> ;	       BITS 5 THRU 0 - MAXIMUM SECTORS PER TRACK
   357                              <1> ;	(DL) - DRIVE NUMBER (0-1 ALLOWED, VALUE CHACKED)
   358                              <1> ;	OUTPUT REGISTERS:
   359                              <1> ;	(ES:DI) - POINTER TO DRIVE PARAMETERS TABLE FOR THIS MEDIA TYPE,
   360                              <1> ;		  UNCHANGED IF (AH) IS NON-ZERO
   361                              <1> ;	(AH) - 00H, CY = 0, TRACK AND SECTORS/TRACK COMBINATION IS SUPPORTED
   362                              <1> ;	     - 01H, CY = 1, FUNCTION IS NOT AVAILABLE
   363                              <1> ;	     - 0CH, CY = 1, TRACK AND SECTORS/TRACK COMBINATION IS NOT SUPPORTED
   364                              <1> ;	     - 80H, CY = 1, TIME OUT (DISKETTE NOT PRESENT)		
   365                              <1> ;-------------------------------------------------------------------------------
   366                              <1> ;	DISK CHANGE STATUS IS ONLY CHECKED WHEN A MEDIA SPECIFIED IS OTHER
   367                              <1> ;	THAN 360 KB DRIVE. IF THE DISK CHANGE LINE IS FOUND TO BE
   368                              <1> ;	ACTIVE THE FOLLOWING ACTIONS TAKE PLACE:
   369                              <1> ;		ATTEMPT TO RESET DISK CHANGE LINE TO INACTIVE STATE. 
   370                              <1> ;		IF ATTEMPT SUCCEEDS SET DASD TYPE FOR FORMAT AND RETURN DISK 
   371                              <1> ;		CHANGE ERROR CODE
   372                              <1> ;		IF ATTEMPT FAILS RETURN TIMEOUT ERROR CODE AND SET DASD TYPE 
   373                              <1> ;		TO A PREDETERMINED STATE INDICATING MEDIA TYPE UNKNOWN.
   374                              <1> ;	IF THE DISK CHANGE LINE IN INACTIVE PERFORM SET DASD TYPE FOR FORMAT.
   375                              <1> ;
   376                              <1> ; DATA VARIABLE -- @DISK_POINTER
   377                              <1> ;	DOUBLE WORD POINTER TO THE CURRENT SET OF DISKETTE PARAMETERS
   378                              <1> ;-------------------------------------------------------------------------------
   379                              <1> ; OUTPUT FOR ALL FUNCTIONS
   380                              <1> ;	AH = STATUS OF OPERATION
   381                              <1> ;		STATUS BITS ARE DEFINED IN THE EQUATES FOR @DISKETTE_STATUS
   382                              <1> ;		VARIABLE IN THE DATA SEGMENT OF THIS MODULE
   383                              <1> ;	CY = 0	SUCCESSFUL OPERATION (AH=0 ON RETURN, EXCEPT FOR READ DASD
   384                              <1> ;		TYPE AH=(15)).
   385                              <1> ;	CY = 1	FAILED OPERATION (AH HAS ERROR REASON)
   386                              <1> ;	FOR READ/WRITE/VERIFY
   387                              <1> ;		DS,BX,DX,CX PRESERVED
   388                              <1> ;	NOTE: IF AN ERROR IS REPORTED BY THE DISKETTE CODE, THE APPROPRIATE 
   389                              <1> ;		ACTION IS TO RESET THE DISKETTE, THEN RETRY THE OPERATION.
   390                              <1> ;		ON READ ACCESSES, NO MOTOR START DELAY IS TAKEN, SO THAT 
   391                              <1> ;		THREE RETRIES ARE REQUIRED ON READS TO ENSURE THAT THE 
   392                              <1> ;		PROBLEM IS NOT DUE TO MOTOR START-UP.
   393                              <1> ;-------------------------------------------------------------------------------
   394                              <1> ;
   395                              <1> ; DISKETTE STATE MACHINE - ABSOLUTE ADDRESS 40:90 (DRIVE A) & 91 (DRIVE B)
   396                              <1> ;
   397                              <1> ;   -----------------------------------------------------------------
   398                              <1> ;   |       |       |       |       |       |       |       |       |
   399                              <1> ;   |   7   |   6   |   5   |   4   |   3   |   2   |   1   |   0   |
   400                              <1> ;   |       |       |       |       |       |       |       |       |
   401                              <1> ;   -----------------------------------------------------------------
   402                              <1> ;	|	|	|	|	|	|	|	|
   403                              <1> ;	|	|	|	|	|	-----------------
   404                              <1> ;	|	|	|	|	|		|
   405                              <1> ;	|	|	|	|    RESERVED		|
   406                              <1> ;	|	|	|	|		  PRESENT STATE
   407                              <1> ;	|	|	|	|	000: 360K IN 360K DRIVE UNESTABLISHED
   408                              <1> ;	|	|	|	|	001: 360K IN 1.2M DRIVE UNESTABLISHED
   409                              <1> ;	|	|	|	|	010: 1.2M IN 1.2M DRIVE UNESTABLISHED
   410                              <1> ;	|	|	|	|	011: 360K IN 360K DRIVE ESTABLISHED
   411                              <1> ;	|	|	|	|	100: 360K IN 1.2M DRIVE ESTABLISHED
   412                              <1> ;	|	|	|	|	101: 1.2M IN 1.2M DRIVE ESTABLISHED
   413                              <1> ;	|	|	|	|	110: RESERVED
   414                              <1> ;	|	|	|	|	111: NONE OF THE ABOVE
   415                              <1> ;	|	|	|	|
   416                              <1> ;	|	|	|	------>	MEDIA/DRIVE ESTABLISHED
   417                              <1> ;	|	|	|
   418                              <1> ;	|	|	-------------->	DOUBLE STEPPING REQUIRED (360K IN 1.2M
   419                              <1> ;	|	|			DRIVE)
   420                              <1> ;	|	|
   421                              <1> ;	------------------------------>	DATA TRANSFER RATE FOR THIS DRIVE:
   422                              <1> ;
   423                              <1> ;						00: 500 KBS
   424                              <1> ;						01: 300 KBS
   425                              <1> ;						10: 250 KBS
   426                              <1> ;						11: RESERVED
   427                              <1> ;
   428                              <1> ;
   429                              <1> ;-------------------------------------------------------------------------------
   430                              <1> ; STATE OPERATION STARTED - ABSOLUTE ADDRESS 40:92 (DRIVE A) & 93 (DRIVE B)
   431                              <1> ;-------------------------------------------------------------------------------
   432                              <1> ; PRESENT CYLINDER NUMBER - ABSOLUTE ADDRESS 40:94 (DRIVE A) & 95 (DRIVE B)
   433                              <1> ;-------------------------------------------------------------------------------
   434                              <1> 
   435                              <1> struc MD
   436 00000000 <res 00000001>      <1> 	.SPEC1		resb	1	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   437 00000001 <res 00000001>      <1> 	.SPEC2		resb	1	; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   438 00000002 <res 00000001>      <1> 	.OFF_TIM	resb	1	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   439 00000003 <res 00000001>      <1> 	.BYT_SEC	resb	1	; 512 BYTES/SECTOR
   440 00000004 <res 00000001>      <1> 	.SEC_TRK	resb	1	; EOT (LAST SECTOR ON TRACK)
   441 00000005 <res 00000001>      <1> 	.GAP		resb	1	; GAP LENGTH
   442 00000006 <res 00000001>      <1> 	.DTL		resb	1	; DTL
   443 00000007 <res 00000001>      <1> 	.GAP3		resb	1	; GAP LENGTH FOR FORMAT
   444 00000008 <res 00000001>      <1> 	.FIL_BYT	resb	1	; FILL BYTE FOR FORMAT
   445 00000009 <res 00000001>      <1> 	.HD_TIM		resb	1	; HEAD SETTLE TIME (MILLISECONDS)
   446 0000000A <res 00000001>      <1> 	.STR_TIM	resb	1	; MOTOR START TIME (1/8 SECONDS)
   447 0000000B <res 00000001>      <1> 	.MAX_TRK	resb	1	; MAX. TRACK NUMBER
   448 0000000C <res 00000001>      <1> 	.RATE		resb	1	; DATA TRANSFER RATE
   449                              <1> endstruc
   450                              <1> 
   451                              <1> BIT7OFF	EQU	7FH
   452                              <1> BIT7ON	EQU	80H
   453                              <1> 
   454                              <1> ; 30/08/2020 - TRDOS 386 v2
   455                              <1> 
   456                              <1> ;;int13h: ; 16/02/2015
   457                              <1> ;; 16/02/2015 - 21/02/2015
   458                              <1> int40h:
   459 00003A8B 9C                  <1> 	pushfd
   460 00003A8C 0E                  <1> 	push 	cs
   461 00003A8D E801000000          <1> 	call 	DISKETTE_IO_1
   462 00003A92 C3                  <1> 	retn	
   463                              <1> 
   464                              <1> DISKETTE_IO_1:
   465                              <1> 
   466 00003A93 FB                  <1> 	STI				; INTERRUPTS BACK ON
   467 00003A94 55                  <1> 	PUSH	eBP			; USER REGISTER
   468 00003A95 57                  <1> 	PUSH	eDI			; USER REGISTER
   469 00003A96 52                  <1> 	PUSH	eDX			; HEAD #, DRIVE # OR USER REGISTER
   470 00003A97 53                  <1> 	PUSH	eBX			; BUFFER OFFSET PARAMETER OR REGISTER
   471 00003A98 51                  <1> 	PUSH	eCX			; TRACK #-SECTOR # OR USER REGISTER
   472 00003A99 89E5                <1> 	MOV	eBP,eSP			; BP     => PARAMETER LIST DEP. ON AH
   473                              <1> 					; [BP]   = SECTOR #
   474                              <1> 					; [BP+1] = TRACK #
   475                              <1> 					; [BP+2] = BUFFER OFFSET
   476                              <1> 					; FOR RETURN OF DRIVE PARAMETERS:
   477                              <1> 					; CL/[BP] = BITS 7&6 HI BITS OF MAX CYL
   478                              <1> 					; 	    BITS 0-5 MAX SECTORS/TRACK
   479                              <1> 					; CH/[BP+1] = LOW 8 BITS OF MAX CYL.
   480                              <1> 					; BL/[BP+2] = BITS 7-4 = 0
   481                              <1> 					;	      BITS 3-0 = VALID CMOS TYPE
   482                              <1> 					; BH/[BP+3] = 0
   483                              <1> 					; DL/[BP+4] = # DRIVES INSTALLED
   484                              <1> 					; DH/[BP+5] = MAX HEAD #
   485                              <1> 					; DI/[BP+6] = OFFSET TO DISK BASE
   486 00003A9B 06                  <1> 	push	es ; 06/02/2015	
   487 00003A9C 1E                  <1> 	PUSH	DS			; BUFFER SEGMENT PARM OR USER REGISTER
   488 00003A9D 56                  <1> 	PUSH	eSI			; USER REGISTERS
   489                              <1> 	;CALL	DDS			; SEGMENT OF BIOS DATA AREA TO DS
   490                              <1> 	;mov	cx, cs
   491                              <1> 	;mov	ds, cx
   492 00003A9E 66B91000            <1> 	mov	cx, KDATA
   493 00003AA2 8ED9                <1>         mov     ds, cx
   494 00003AA4 8EC1                <1>         mov     es, cx
   495                              <1> 
   496                              <1> 	;CMP	AH,(FNC_TAE-FNC_TAB)/2	; CHECK FOR > LARGEST FUNCTION
   497 00003AA6 80FC19              <1> 	cmp	ah,(FNC_TAE-FNC_TAB)/4  ; 18/02/2015
   498 00003AA9 7202                <1> 	JB	short OK_FUNC		; FUNCTION OK
   499 00003AAB B414                <1> 	MOV	AH,14H			; REPLACE WITH KNOWN INVALID FUNCTION
   500                              <1> OK_FUNC:
   501 00003AAD 80FC01              <1> 	CMP	AH,1			; RESET OR STATUS ?
   502 00003AB0 760C                <1> 	JBE	short OK_DRV		; IF RESET OR STATUS DRIVE ALWAYS OK
   503 00003AB2 80FC08              <1> 	CMP	AH,8			; READ DRIVE PARMS ?
   504 00003AB5 7407                <1> 	JZ	short OK_DRV		; IF SO DRIVE CHECKED LATER
   505 00003AB7 80FA01              <1> 	CMP	DL,1			; DRIVES 0 AND 1 OK
   506 00003ABA 7602                <1> 	JBE	short OK_DRV		; IF 0 OR 1 THEN JUMP
   507 00003ABC B414                <1> 	MOV	AH,14H			; REPLACE WITH KNOWN INVALID FUNCTION
   508                              <1> OK_DRV:
   509 00003ABE 31C9                <1> 	xor	ecx, ecx
   510                              <1> 	;mov	esi, ecx ; 08/02/2015
   511 00003AC0 89CF                <1> 	mov	edi, ecx ; 08/02/2015
   512 00003AC2 88E1                <1> 	MOV	CL,AH			; CL = FUNCTION
   513                              <1> 	;XOR	CH,CH			; CX = FUNCTION
   514                              <1> 	;SHL	CL, 1			; FUNCTION TIMES 2
   515 00003AC4 C0E102              <1> 	SHL	CL, 2 ; 20/02/2015	; FUNCTION TIMES 4 (for 32 bit offset)
   516 00003AC7 BB[FF3A0000]        <1> 	MOV	eBX,FNC_TAB		; LOAD START OF FUNCTION TABLE
   517 00003ACC 01CB                <1> 	ADD	eBX,eCX			; ADD OFFSET INTO TABLE => ROUTINE
   518 00003ACE 88F4                <1> 	MOV	AH,DH			; AX = HEAD #,# OF SECTORS OR DASD TYPE
   519 00003AD0 30F6                <1> 	XOR	DH,DH			; DX = DRIVE #
   520 00003AD2 6689C6              <1> 	MOV	SI,AX			; SI = HEAD #,# OF SECTORS OR DASD TYPE
   521 00003AD5 6689D7              <1> 	MOV     DI,DX                   ; DI = DRIVE #
   522                              <1> 	;
   523                              <1> 	; 11/12/2014
   524 00003AD8 8815[9D640000]      <1>         mov     [cfd], dl               ; current floppy drive (for 'GET_PARM')        
   525                              <1> 	;
   526 00003ADE 8A25[085F0100]      <1> 	MOV	AH, [DSKETTE_STATUS]	; LOAD STATUS TO AH FOR STATUS FUNCTION
   527 00003AE4 C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS],0	; INITIALIZE FOR ALL OTHERS
   528                              <1> 
   529                              <1> ;	THROUGHOUT THE DISKETTE BIOS, THE FOLLOWING INFORMATION IS CONTAINED IN
   530                              <1> ;	THE FOLLOWING MEMORY LOCATIONS AND REGISTERS. NOT ALL DISKETTE BIOS
   531                              <1> ;	FUNCTIONS REQUIRE ALL OF THESE PARAMETERS.
   532                              <1> ;
   533                              <1> ;		DI	: DRIVE #
   534                              <1> ;		SI-HI	: HEAD #
   535                              <1> ;		SI-LOW	: # OF SECTORS OR DASD TYPE FOR FORMAT
   536                              <1> ;		ES	: BUFFER SEGMENT
   537                              <1> ;		[BP]	: SECTOR #
   538                              <1> ;		[BP+1]	: TRACK #
   539                              <1> ;		[BP+2]	: BUFFER OFFSET
   540                              <1> ;
   541                              <1> ;	ACROSS CALLS TO SUBROUTINES THE CARRY FLAG (CY=1), WHERE INDICATED IN 
   542                              <1> ;	SUBROUTINE PROLOGUES, REPRESENTS AN EXCEPTION RETURN (NORMALLY AN ERROR 
   543                              <1> ;	CONDITION). IN MOST CASES, WHEN CY = 1, @DSKETTE_STATUS CONTAINS THE 
   544                              <1> ;	SPECIFIC ERROR CODE.
   545                              <1> ;
   546                              <1> 					; (AH) = @DSKETTE_STATUS
   547 00003AEB FF13                <1> 	CALL	dWORD [eBX]		; CALL THE REQUESTED FUNCTION
   548 00003AED 5E                  <1> 	POP	eSI			; RESTORE ALL REGISTERS
   549 00003AEE 1F                  <1> 	POP	DS
   550 00003AEF 07                  <1> 	pop	es	; 06/02/2015
   551 00003AF0 59                  <1> 	POP	eCX
   552 00003AF1 5B                  <1> 	POP	eBX
   553 00003AF2 5A                  <1> 	POP	eDX
   554 00003AF3 5F                  <1> 	POP	eDI
   555 00003AF4 89E5                <1> 	MOV	eBP, eSP
   556 00003AF6 50                  <1> 	PUSH	eAX
   557 00003AF7 9C                  <1> 	PUSHFd
   558 00003AF8 58                  <1> 	POP	eAX
   559                              <1> 	;MOV	[BP+6], AX
   560 00003AF9 89450C              <1> 	mov	[ebp+12], eax  ; 18/02/2015, flags
   561 00003AFC 58                  <1> 	POP	eAX
   562 00003AFD 5D                  <1> 	POP	eBP
   563 00003AFE CF                  <1> 	IRETd
   564                              <1> 
   565                              <1> ;-------------------------------------------------------------------------------
   566                              <1> ; DW --> dd (06/02/2015)
   567 00003AFF [633B0000]          <1> FNC_TAB	dd	DSK_RESET		; AH = 00H; RESET
   568 00003B03 [DC3B0000]          <1> 	dd	DSK_STATUS		; AH = 01H; STATUS
   569 00003B07 [ED3B0000]          <1> 	dd	DSK_READ		; AH = 02H; READ
   570 00003B0B [FE3B0000]          <1> 	dd	DSK_WRITE		; AH = 03H; WRITE
   571 00003B0F [0F3C0000]          <1> 	dd	DSK_VERF		; AH = 04H; VERIFY
   572 00003B13 [203C0000]          <1> 	dd	DSK_FORMAT		; AH = 05H; FORMAT
   573 00003B17 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 06H; INVALID
   574 00003B1B [A53C0000]          <1> 	dd	FNC_ERR			; AH = 07H; INVALID
   575 00003B1F [B23C0000]          <1> 	dd	DSK_PARMS		; AH = 08H; READ DRIVE PARAMETERS
   576 00003B23 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 09H; INVALID
   577 00003B27 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0AH; INVALID
   578 00003B2B [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0BH; INVALID
   579 00003B2F [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0CH; INVALID
   580 00003B33 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0DH; INVALID
   581 00003B37 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0EH; INVALID
   582 00003B3B [A53C0000]          <1> 	dd	FNC_ERR			; AH = 0FH; INVALID
   583 00003B3F [A53C0000]          <1> 	dd	FNC_ERR			; AH = 10H; INVALID
   584 00003B43 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 11H; INVALID
   585 00003B47 [A53C0000]          <1> 	dd	FNC_ERR			; AH = 12H; INVALID
   586 00003B4B [A53C0000]          <1> 	dd	FNC_ERR			; AH = 13H; INVALID
   587 00003B4F [A53C0000]          <1> 	dd	FNC_ERR			; AH = 14H; INVALID
   588 00003B53 [A23D0000]          <1> 	dd	DSK_TYPE		; AH = 15H; READ DASD TYPE
   589 00003B57 [D23D0000]          <1> 	dd	DSK_CHANGE		; AH = 16H; CHANGE STATUS
   590 00003B5B [0C3E0000]          <1> 	dd	FORMAT_SET		; AH = 17H; SET DASD TYPE
   591 00003B5F [8F3E0000]          <1> 	dd	SET_MEDIA		; AH = 18H; SET MEDIA TYPE	
   592                              <1> FNC_TAE EQU     $                       ; END
   593                              <1> 
   594                              <1> ;-------------------------------------------------------------------------------
   595                              <1> ; DISK_RESET	(AH = 00H)	
   596                              <1> ;		RESET THE DISKETTE SYSTEM.
   597                              <1> ;
   598                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   599                              <1> ;-------------------------------------------------------------------------------
   600                              <1> DSK_RESET:
   601 00003B63 66BAF203            <1> 	MOV	DX,03F2H		; ADAPTER CONTROL PORT
   602 00003B67 FA                  <1> 	CLI				; NO INTERRUPTS
   603 00003B68 A0[065F0100]        <1> 	MOV	AL,[MOTOR_STATUS]	; GET DIGITAL OUTPUT REGISTER REFLECTION
   604 00003B6D 243F                <1> 	AND	AL,00111111B		; KEEP SELECTED AND MOTOR ON BITS
   605 00003B6F C0C004              <1> 	ROL	AL,4			; MOTOR VALUE TO HIGH NIBBLE
   606                              <1> 					; DRIVE SELECT TO LOW NIBBLE
   607 00003B72 0C08                <1> 	OR	AL,00001000B		; TURN ON INTERRUPT ENABLE
   608 00003B74 EE                  <1> 	OUT	DX,AL			; RESET THE ADAPTER
   609 00003B75 C605[055F0100]00    <1> 	MOV	byte [SEEK_STATUS],0	; SET RECALIBRATE REQUIRED ON ALL DRIVES
   610                              <1> 	;JMP	$+2			; WAIT FOR I/O
   611                              <1> 	;JMP	$+2			; WAIT FOR I/O (TO INSURE MINIMUM
   612                              <1> 					;      PULSE WIDTH)
   613                              <1> 	; 19/12/2014
   614                              <1> 	NEWIODELAY
   614 00003B7C E6EB                <2>  out 0ebh,al
   615                              <1> 
   616                              <1> 	; 17/12/2014 
   617                              <1> 	; AWARD BIOS 1999 - RESETDRIVES (ADISK.ASM)
   618 00003B7E B915000000          <1> 	mov	ecx, WAITCPU_RESET_ON	; cx = 21 -- Min. 14 micro seconds !?
   619                              <1> wdw1:
   620                              <1> 	NEWIODELAY   ; 27/02/2015
   620 00003B83 E6EB                <2>  out 0ebh,al
   621 00003B85 E2FC                <1> 	loop	wdw1
   622                              <1> 	;
   623 00003B87 0C04                <1> 	OR	AL,00000100B		; TURN OFF RESET BIT
   624 00003B89 EE                  <1> 	OUT	DX,AL			; RESET THE ADAPTER
   625                              <1> 	; 16/12/2014
   626                              <1> 	IODELAY
   626 00003B8A EB00                <2>  jmp short $+2
   626 00003B8C EB00                <2>  jmp short $+2
   627                              <1> 	;
   628                              <1> 	;STI				; ENABLE THE INTERRUPTS
   629 00003B8E E8590C0000          <1> 	CALL	WAIT_INT		; WAIT FOR THE INTERRUPT
   630 00003B93 723E                <1> 	JC	short DR_ERR		; IF ERROR, RETURN IT
   631 00003B95 66B9C000            <1> 	MOV	CX,11000000B		; CL = EXPECTED @NEC_STATUS
   632                              <1> NXT_DRV:
   633 00003B99 6651                <1> 	PUSH	CX			; SAVE FOR CALL
   634 00003B9B B8[D13B0000]        <1> 	MOV	eAX, DR_POP_ERR 	; LOAD NEC_OUTPUT ERROR ADDRESS
   635 00003BA0 50                  <1> 	PUSH	eAX			; "
   636 00003BA1 B408                <1> 	MOV	AH,08H			; SENSE INTERRUPT STATUS COMMAND
   637 00003BA3 E8370B0000          <1> 	CALL	NEC_OUTPUT
   638 00003BA8 58                  <1> 	POP	eAX			; THROW AWAY ERROR RETURN
   639 00003BA9 E86E0C0000          <1> 	CALL	RESULTS			; READ IN THE RESULTS
   640 00003BAE 6659                <1> 	POP	CX			; RESTORE AFTER CALL
   641 00003BB0 7221                <1> 	JC	short DR_ERR		; ERROR RETURN
   642 00003BB2 3A0D[095F0100]      <1> 	CMP	CL, [NEC_STATUS]	; TEST FOR DRIVE READY TRANSITION
   643 00003BB8 7519                <1> 	JNZ	short DR_ERR		; EVERYTHING OK
   644 00003BBA FEC1                <1> 	INC	CL			; NEXT EXPECTED @NEC_STATUS
   645 00003BBC 80F9C3              <1> 	CMP	CL,11000011B		; ALL POSSIBLE DRIVES CLEARED
   646 00003BBF 76D8                <1> 	JBE	short NXT_DRV		; FALL THRU IF 11000100B OR >
   647                              <1> 	;
   648 00003BC1 E886030000          <1> 	CALL	SEND_SPEC		; SEND SPECIFY COMMAND TO NEC
   649                              <1> RESBAC:
   650 00003BC6 E83A090000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
   651 00003BCB 6689F3              <1> 	MOV	BX,SI			; GET SAVED AL TO BL
   652 00003BCE 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
   653 00003BD0 C3                  <1> 	RETn		
   654                              <1> DR_POP_ERR:
   655 00003BD1 6659                <1> 	POP	CX			; CLEAR STACK
   656                              <1> DR_ERR:
   657 00003BD3 800D[085F0100]20    <1> 	OR	byte [DSKETTE_STATUS],BAD_NEC ; SET ERROR CODE
   658 00003BDA EBEA                <1> 	JMP	SHORT RESBAC		; RETURN FROM RESET
   659                              <1> 
   660                              <1> ;-------------------------------------------------------------------------------
   661                              <1> ; DISK_STATUS	(AH = 01H)
   662                              <1> ;	DISKETTE STATUS.
   663                              <1> ;
   664                              <1> ; ON ENTRY:	AH : STATUS OF PREVIOUS OPERATION
   665                              <1> ;
   666                              <1> ; ON EXIT:	AH, @DSKETTE_STATUS, CY REFLECT STATUS OF PREVIOUS OPERATION.
   667                              <1> ;-------------------------------------------------------------------------------
   668                              <1> DSK_STATUS:
   669 00003BDC 8825[085F0100]      <1> 	MOV	[DSKETTE_STATUS],AH	; PUT BACK FOR SETUP END
   670 00003BE2 E81E090000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
   671 00003BE7 6689F3              <1> 	MOV	BX,SI			; GET SAVED AL TO BL
   672 00003BEA 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
   673 00003BEC C3                  <1> 	RETn		
   674                              <1> 
   675                              <1> ;-------------------------------------------------------------------------------
   676                              <1> ; DISK_READ	(AH = 02H)	
   677                              <1> ;	DISKETTE READ.
   678                              <1> ;
   679                              <1> ; ON ENTRY:	DI	: DRIVE #
   680                              <1> ;		SI-HI	: HEAD #
   681                              <1> ;		SI-LOW	: # OF SECTORS
   682                              <1> ;		ES	: BUFFER SEGMENT
   683                              <1> ;		[BP]	: SECTOR #
   684                              <1> ;		[BP+1]	: TRACK #
   685                              <1> ;		[BP+2]	: BUFFER OFFSET
   686                              <1> ;
   687                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   688                              <1> ;-------------------------------------------------------------------------------
   689                              <1> 
   690                              <1> ; 06/02/2015, ES:BX -> EBX (unix386.s)
   691                              <1> 
   692                              <1> DSK_READ:
   693 00003BED 8025[065F0100]7F    <1> 	AND	byte [MOTOR_STATUS],01111111B ; INDICATE A READ OPERATION
   694 00003BF4 66B846E6            <1> 	MOV	AX,0E646H		; AX = NEC COMMAND, DMA COMMAND
   695 00003BF8 E859040000          <1> 	CALL	RD_WR_VF		; COMMON READ/WRITE/VERIFY
   696 00003BFD C3                  <1> 	RETn
   697                              <1> 
   698                              <1> ;-------------------------------------------------------------------------------
   699                              <1> ; DISK_WRITE	(AH = 03H)
   700                              <1> ;	DISKETTE WRITE.
   701                              <1> ;
   702                              <1> ; ON ENTRY:	DI	: DRIVE #
   703                              <1> ;		SI-HI	: HEAD #
   704                              <1> ;		SI-LOW	: # OF SECTORS
   705                              <1> ;		ES	: BUFFER SEGMENT
   706                              <1> ;		[BP]	: SECTOR #
   707                              <1> ;		[BP+1]	: TRACK #
   708                              <1> ;		[BP+2]	: BUFFER OFFSET
   709                              <1> ;
   710                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   711                              <1> ;-------------------------------------------------------------------------------
   712                              <1> 
   713                              <1> ; 06/02/2015, ES:BX -> EBX (unix386.s)
   714                              <1> 
   715                              <1> DSK_WRITE:
   716 00003BFE 66B84AC5            <1> 	MOV	AX,0C54AH		; AX = NEC COMMAND, DMA COMMAND
   717 00003C02 800D[065F0100]80    <1>         OR      byte [MOTOR_STATUS],10000000B ; INDICATE WRITE OPERATION
   718 00003C09 E848040000          <1> 	CALL	RD_WR_VF		; COMMON READ/WRITE/VERIFY
   719 00003C0E C3                  <1> 	RETn
   720                              <1> 
   721                              <1> ;-------------------------------------------------------------------------------
   722                              <1> ; DISK_VERF	(AH = 04H)
   723                              <1> ;	DISKETTE VERIFY.
   724                              <1> ;
   725                              <1> ; ON ENTRY:	DI	: DRIVE #
   726                              <1> ;		SI-HI	: HEAD #
   727                              <1> ;		SI-LOW	: # OF SECTORS
   728                              <1> ;		ES	: BUFFER SEGMENT
   729                              <1> ;		[BP]	: SECTOR #
   730                              <1> ;		[BP+1]	: TRACK #
   731                              <1> ;		[BP+2]	: BUFFER OFFSET
   732                              <1> ;
   733                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   734                              <1> ;-------------------------------------------------------------------------------
   735                              <1> DSK_VERF:
   736 00003C0F 8025[065F0100]7F    <1> 	AND	byte [MOTOR_STATUS],01111111B ; INDICATE A READ OPERATION
   737 00003C16 66B842E6            <1> 	MOV	AX,0E642H		; AX = NEC COMMAND, DMA COMMAND
   738 00003C1A E837040000          <1> 	CALL	RD_WR_VF		; COMMON READ/WRITE/VERIFY
   739 00003C1F C3                  <1> 	RETn
   740                              <1> 
   741                              <1> ;-------------------------------------------------------------------------------
   742                              <1> ; DISK_FORMAT	(AH = 05H)
   743                              <1> ;	DISKETTE FORMAT.
   744                              <1> ;
   745                              <1> ; ON ENTRY:	DI	: DRIVE #
   746                              <1> ;		SI-HI	: HEAD #
   747                              <1> ;		SI-LOW	: # OF SECTORS
   748                              <1> ;		ES	: BUFFER SEGMENT
   749                              <1> ;		[BP]	: SECTOR #
   750                              <1> ;		[BP+1]	: TRACK #
   751                              <1> ;		[BP+2]	: BUFFER OFFSET
   752                              <1> ;		@DISK_POINTER POINTS TO THE PARAMETER TABLE OF THIS DRIVE
   753                              <1> ;
   754                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   755                              <1> ;-------------------------------------------------------------------------------
   756                              <1> DSK_FORMAT:
   757 00003C20 E870030000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
   758 00003C25 E86C050000          <1> 	CALL	FMT_INIT		; ESTABLISH STATE IF UNESTABLISHED
   759 00003C2A 800D[065F0100]80    <1>         OR      byte [MOTOR_STATUS], 10000000B ; INDICATE WRITE OPERATION
   760 00003C31 E8B4050000          <1> 	CALL	MED_CHANGE		; CHECK MEDIA CHANGE AND RESET IF SO
   761 00003C36 725D                <1>         JC      short FM_DON            ; MEDIA CHANGED, SKIP
   762 00003C38 E80F030000          <1> 	CALL	SEND_SPEC		; SEND SPECIFY COMMAND TO NEC
   763 00003C3D E81A060000          <1> 	CALL	CHK_LASTRATE		; ZF=1 ATTEMPT RATE IS SAME AS LAST RATE
   764 00003C42 7405                <1>         JZ      short FM_WR             ; YES, SKIP SPECIFY COMMAND
   765 00003C44 E8F1050000          <1> 	CALL	SEND_RATE		; SEND DATA RATE TO CONTROLLER
   766                              <1> FM_WR:
   767 00003C49 E8A7060000          <1> 	CALL	FMTDMA_SET		; SET UP THE DMA FOR FORMAT
   768 00003C4E 7245                <1>         JC      short FM_DON            ; RETURN WITH ERROR
   769 00003C50 B44D                <1> 	MOV	AH,04DH			; ESTABLISH THE FORMAT COMMAND
   770 00003C52 E804070000          <1> 	CALL	NEC_INIT		; INITIALIZE THE NEC
   771 00003C57 723C                <1>         JC      short FM_DON            ; ERROR - EXIT
   772 00003C59 B8[953C0000]        <1>         MOV     eAX, FM_DON             ; LOAD ERROR ADDRESS
   773 00003C5E 50                  <1> 	PUSH	eAX			; PUSH NEC_OUT ERROR RETURN
   774 00003C5F B203                <1> 	MOV	DL,3			; BYTES/SECTOR VALUE TO NEC
   775 00003C61 E873090000          <1> 	CALL	GET_PARM
   776 00003C66 E8740A0000          <1> 	CALL	NEC_OUTPUT
   777 00003C6B B204                <1> 	MOV	DL,4			; SECTORS/TRACK VALUE TO NEC
   778 00003C6D E867090000          <1> 	CALL	GET_PARM
   779 00003C72 E8680A0000          <1> 	CALL	NEC_OUTPUT
   780 00003C77 B207                <1> 	MOV	DL,7			; GAP LENGTH VALUE TO NEC
   781 00003C79 E85B090000          <1> 	CALL	GET_PARM
   782 00003C7E E85C0A0000          <1> 	CALL	NEC_OUTPUT
   783 00003C83 B208                <1> 	MOV	DL,8			; FILLER BYTE TO NEC
   784 00003C85 E84F090000          <1> 	CALL	GET_PARM
   785 00003C8A E8500A0000          <1> 	CALL	NEC_OUTPUT
   786 00003C8F 58                  <1> 	POP	eAX			; THROW AWAY ERROR
   787 00003C90 E844070000          <1> 	CALL	NEC_TERM		; TERMINATE, RECEIVE STATUS, ETC,
   788                              <1> FM_DON:
   789 00003C95 E82C030000          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
   790 00003C9A E866080000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
   791 00003C9F 6689F3              <1> 	MOV	BX,SI			; GET SAVED AL TO BL
   792 00003CA2 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
   793 00003CA4 C3                  <1> 	RETn
   794                              <1> 
   795                              <1> ;-------------------------------------------------------------------------------
   796                              <1> ; FNC_ERR
   797                              <1> ;	INVALID FUNCTION REQUESTED OR INVALID DRIVE: 
   798                              <1> ;	SET BAD COMMAND IN STATUS.
   799                              <1> ;
   800                              <1> ; ON EXIT: 	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
   801                              <1> ;-------------------------------------------------------------------------------
   802                              <1> FNC_ERR:				; INVALID FUNCTION REQUEST
   803 00003CA5 6689F0              <1> 	MOV	AX,SI			; RESTORE AL
   804 00003CA8 B401                <1> 	MOV	AH,BAD_CMD		; SET BAD COMMAND ERROR
   805 00003CAA 8825[085F0100]      <1> 	MOV	[DSKETTE_STATUS],AH	; STORE IN DATA AREA
   806 00003CB0 F9                  <1> 	STC				; SET CARRY INDICATING ERROR
   807 00003CB1 C3                  <1> 	RETn
   808                              <1> 
   809                              <1> ; 30/08/2020
   810                              <1> ; 29/08/2020
   811                              <1> ; 01/06/2016
   812                              <1> ; 28/05/2016
   813                              <1> ; 27/05/2016 - TRDOS 386 (TRDOS v.2.0)
   814                              <1> ;-------------------------------------------------------------------------------
   815                              <1> ; DISK_PARMS	(AH = 08H)	
   816                              <1> ;	READ DRIVE PARAMETERS.
   817                              <1> ;
   818                              <1> ; ON ENTRY:	DI : DRIVE #
   819                              <1> ;		; 27/05/2016
   820                              <1> ;		EBX = Buffer Address for floppy disk parameters table (16 bytes)
   821                              <1> ;
   822                              <1> ; ON EXIT:	CL/[BP]   = BITS 7 & 6 HI 2 BITS OF MAX CYLINDER
   823                              <1> ;		            BITS 0-5 MAX SECTORS/TRACK
   824                              <1> ;		CH/[BP+1] = LOW 8 BITS OF MAX CYLINDER
   825                              <1> ;		BL/[BP+2] = BITS 7-4 = 0
   826                              <1> ;		            BITS 3-0 = VALID CMOS DRIVE TYPE
   827                              <1> ;		BH/[BP+3] = 0
   828                              <1> ;		DL/[BP+4] = # DRIVES INSTALLED (VALUE CHECKED)
   829                              <1> ;		DH/[BP+5] = MAX HEAD #
   830                              <1> ;	     ** 27/05/2016 - TRDOS 386 (TRDOS v2.0) **	
   831                              <1> ;            ** EBX = Buffer address for floppy disk parameters table **
   832                              <1> ;		;DI/[BP+6] = OFFSET TO DISK_BASE
   833                              <1> ;		;ES        = SEGMENT OF DISK_BASE
   834                              <1> ;
   835                              <1> ;		AX        = 0
   836                              <1> ;
   837                              <1> ;		NOTE : THE ABOVE INFORMATION IS STORED IN THE USERS STACK AT
   838                              <1> ;		       THE LOCATIONS WHERE THE MAIN ROUTINE WILL POP THEM
   839                              <1> ;		       INTO THE APPROPRIATE REGISTERS BEFORE RETURNING TO THE
   840                              <1> ;		       CALLER.
   841                              <1> ;-------------------------------------------------------------------------------
   842                              <1> DSK_PARMS:
   843 00003CB2 E8DE020000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH,
   844                              <1>      ;	MOV	WORD [BP+2],0		; DRIVE TYPE = 0
   845                              <1>      ;  MOV     AX, [EQUIP_FLAG]        ; LOAD EQUIPMENT FLAG FOR # DISKETTES
   846                              <1>      ;  AND     AL,11000001B            ; KEEP DISKETTE DRIVE BITS
   847                              <1>      ;  MOV     DL,2                    ; DISKETTE DRIVES = 2
   848                              <1>      ;  CMP     AL,01000001B            ; 2 DRIVES INSTALLED ?
   849                              <1>      ;  JZ      short STO_DL            ; IF YES JUMP
   850                              <1>      ;  DEC     DL                      ; DISKETTE DRIVES = 1
   851                              <1>      ;  CMP     AL,00000001B            ; 1 DRIVE INSTALLED ?
   852                              <1>      ;  JNZ     short NON_DRV           ; IF NO JUMP
   853 00003CB7 29D2                <1> 	sub	edx, edx
   854 00003CB9 66A1[AE640000]      <1> 	mov     ax, [fd0_type]
   855 00003CBF 6621C0              <1> 	and     ax, ax
   856 00003CC2 0F849B000000        <1>         jz      NON_DRV
   857 00003CC8 FEC2                <1> 	inc     dl
   858 00003CCA 20E4                <1> 	and     ah, ah
   859 00003CCC 7402                <1> 	jz      short STO_DL
   860 00003CCE FEC2                <1> 	inc     dl
   861                              <1> STO_DL:
   862                              <1> 	; 30/08/2020
   863 00003CD0 6639FA              <1> 	cmp	dx, di
   864 00003CD3 0F868A000000        <1> 	jna	NON_DRV
   865                              <1> 	;
   866                              <1> 	;MOV	[BP+4],DL		; STORE NUMBER OF DRIVES
   867 00003CD9 895508              <1> 	mov	[ebp+8], edx ; 20/02/2015	 	
   868 00003CDC 6683FF01            <1> 	CMP	DI,1			; CHECK FOR VALID DRIVE
   869                              <1> 	;JA	short NON_DRV1		; DRIVE INVALID
   870 00003CE0 0F8780000000        <1> 	ja	NON_DRV1 ; 29/08/2020
   871                              <1> 	;MOV	BYTE [BP+5],1		; MAXIMUM HEAD NUMBER =	1
   872 00003CE6 C6450901            <1> 	mov	byte [ebp+9], 1  ; 20/02/2015	
   873 00003CEA E8E1080000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN AL
   874                              <1> 	;;20/02/2015
   875                              <1> 	;;JC	short CHK_EST		; IF CMOS BAD CHECKSUM ESTABLISHED
   876                              <1> 	;;OR	AL,AL			; TEST FOR NO DRIVE TYPE
   877 00003CEF 740F                <1> 	JZ	short CHK_EST		; JUMP IF SO
   878 00003CF1 E82B020000          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL
   879 00003CF6 7208                <1> 	JC	short CHK_EST		; TYPE NOT IN TABLE (POSSIBLE BAD CMOS)
   880                              <1> 	;MOV	[BP+2],AL		; STORE VALID CMOS DRIVE TYPE
   881                              <1>         ;mov	[ebp+4], al ; 06/02/2015
   882 00003CF8 8A4B04              <1> 	MOV     CL, [eBX+MD.SEC_TRK]     ; GET SECTOR/TRACK
   883 00003CFB 8A6B0B              <1>         MOV     CH, [eBX+MD.MAX_TRK]     ; GET MAX. TRACK NUMBER
   884 00003CFE EB36                <1> 	JMP	SHORT STO_CX		; CMOS GOOD, USE CMOS
   885                              <1> CHK_EST:
   886 00003D00 8AA7[155F0100]      <1> 	MOV	AH, [DSK_STATE+eDI]	; LOAD STATE FOR THIS DRIVE
   887 00003D06 F6C410              <1> 	TEST	AH,MED_DET		; CHECK FOR ESTABLISHED STATE
   888 00003D09 745B                <1> 	JZ	short NON_DRV1		; CMOS BAD/INVALID OR UNESTABLISHED
   889                              <1> USE_EST:
   890 00003D0B 80E4C0              <1> 	AND	AH,RATE_MSK		; ISOLATE STATE
   891 00003D0E 80FC80              <1> 	CMP	AH,RATE_250		; RATE 250 ?
   892 00003D11 757B                <1> 	JNE	short USE_EST2		; NO, GO CHECK OTHER RATE
   893                              <1> 
   894                              <1> ;-----	DATA RATE IS 250 KBS, TRY 360 KB TABLE FIRST
   895                              <1> 
   896 00003D13 B001                <1> 	MOV	AL,01			; DRIVE TYPE 1 (360KB)
   897 00003D15 E807020000          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL
   898 00003D1A 8A4B04              <1>         MOV     CL, [eBX+MD.SEC_TRK]    ; GET SECTOR/TRACK
   899 00003D1D 8A6B0B              <1>         MOV     CH, [eBX+MD.MAX_TRK]    ; GET MAX. TRACK NUMBER
   900 00003D20 F687[155F0100]01    <1> 	TEST	byte [DSK_STATE+eDI],TRK_CAPA ; 80 TRACK ?
   901 00003D27 740D                <1> 	JZ	short STO_CX		; MUST BE 360KB DRIVE 
   902                              <1> 
   903                              <1> ;-----	IT IS 1.44 MB DRIVE
   904                              <1> 
   905                              <1> PARM144:
   906 00003D29 B004                <1> 	MOV	AL,04			; DRIVE TYPE 4 (1.44MB)
   907 00003D2B E8F1010000          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL
   908 00003D30 8A4B04              <1>         MOV     CL, [eBX+MD.SEC_TRK]    ; GET SECTOR/TRACK
   909 00003D33 8A6B0B              <1>         MOV     CH, [eBX+MD.MAX_TRK]    ; GET MAX. TRACK NUMBER
   910                              <1> STO_CX:
   911 00003D36 894D00              <1> 	MOV	[eBP],eCX		; SAVE POINTER IN STACK FOR RETURN
   912                              <1> ES_DI:
   913                              <1> 	;MOV	[BP+6],BX		; ADDRESS OF MEDIA/DRIVE PARM TABLE 
   914                              <1> 	;mov	[ebp+12], ebx ; 06/02/2015
   915                              <1> 	;MOV	AX,CS			; SEGMENT MEDIA/DRIVE PARAMETER TABLE
   916                              <1> 	;MOV	ES,AX			; ES IS SEGMENT OF TABLE
   917                              <1> 	;
   918                              <1> 	; 28/05/2016
   919                              <1> 	; 27/05/2016
   920                              <1> 	; return floppy disk parameters table to user
   921                              <1> 	; in user's buffer, which is pointed by EBX
   922                              <1> 	;
   923 00003D39 57                  <1> 	push	edi
   924 00003D3A 8B7D04              <1> 	mov	edi, [ebp+4]  		; ebx (input), user's buffer address
   925                              <1> 	; 29/08/2020
   926 00003D3D 09FF                <1> 	or	edi, edi
   927 00003D3F 7417                <1> 	jz	short no_copy_fdpt
   928                              <1> 	;
   929 00003D41 0FB6C0              <1> 	movzx	eax, al
   930 00003D44 894504              <1>         mov	[ebp+4], eax   ; ebx	; drive type (for floppy drives)
   931                              <1> 	; 01/06/2016 (INT 33h, disk type return for floppy disks, in BL)
   932 00003D47 A3[0C6B0100]        <1> 	mov	[user_buffer], eax	; 01/06/2016 (overwrite ebx return value)
   933                              <1> 	;(INT 33h, Function 08h will replace user's buffer addr with disk type!)
   934                              <1> 	;
   935 00003D4C 89DE                <1> 	mov	esi, ebx 		; floppy disk parameter table (16 bytes)
   936 00003D4E B910000000          <1> 	mov	ecx, 16 ; 16 bytes
   937 00003D53 E80AB00000          <1>         call    transfer_to_user_buffer ; trdosk6.s (16/05/2016)
   938                              <1> no_copy_fdpt:
   939 00003D58 5F                  <1> 	pop	edi	
   940                              <1> DP_OUT:
   941 00003D59 E868020000          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
   942 00003D5E 6631C0              <1> 	XOR	AX,AX			; CLEAR
   943 00003D61 F8                  <1> 	CLC
   944 00003D62 C3                  <1> 	RETn
   945                              <1> 
   946                              <1> ;-----	NO DRIYE PRESENT HANDLER
   947                              <1> 
   948                              <1> NON_DRV:
   949                              <1> 	;MOV	BYTE [BP+4],0		; CLEAR NUMBER OF DRIVES
   950 00003D63 895508              <1> 	mov	[ebp+8], edx ; 0 ; 20/02/2015
   951                              <1> NON_DRV1:
   952 00003D66 6681FF8000          <1> 	CMP	DI,80H			; CHECK FOR FIXED MEDIA TYPE REQUEST
   953 00003D6B 720C                <1> 	JB	short NON_DRV2		; CONTINUE IF NOT REQUEST FALL THROUGH
   954                              <1> 
   955                              <1> ;-----	FIXED DISK REQUEST FALL THROUGH ERROR
   956                              <1> 	
   957 00003D6D E854020000          <1> 	CALL	XLAT_OLD		; ELSE TRANSLATE TO COMPATIBLE MODE
   958 00003D72 6689F0              <1> 	MOV	AX,SI			; RESTORE AL
   959 00003D75 B401                <1> 	MOV	AH,BAD_CMD		; SET BAD COMMAND ERROR
   960 00003D77 F9                  <1> 	STC
   961 00003D78 C3                  <1> 	RETn
   962                              <1> 
   963                              <1> NON_DRV2:
   964                              <1> 	;XOR	AX,AX			; CLEAR PARMS IF NO DRIVES OR CMOS BAD
   965 00003D79 31C0                <1> 	xor	eax, eax	
   966 00003D7B 66894500            <1> 	MOV	[eBP],AX		; TRACKS, SECTORS/TRACK = 0
   967                              <1> 	;MOV	[BP+5],AH		; HEAD = 0
   968 00003D7F 886509              <1> 	mov	[ebp+9], ah ; 06/02/2015
   969                              <1> 	;MOV	[BP+6],AX		; OFFSET TO DISK_BASE = 0
   970 00003D82 89450C              <1> 	mov	[ebp+12], eax
   971                              <1> 	;;MOV	ES,AX			; ES IS SEGMENT OF TABLE
   972                              <1> 	;JMP	SHORT DP_OUT
   973                              <1> 
   974                              <1> 	; 30/08/2020
   975 00003D85 E83C020000          <1> 	call	XLAT_OLD
   976                              <1> 	;mov	ah, NOT_RDY ; drive not ready
   977 00003D8A B407                <1> 	mov	ah, INIT_FAIL ; DRIVE PARAMETER ACTIVITY FAILED 
   978 00003D8C F9                  <1> 	stc	; cf -> 1, ah = 'drive not ready' error code
   979 00003D8D C3                  <1> 	retn		
   980                              <1> 
   981                              <1> ;-----	DATA RATE IS EITHER 300 KBS OR 500 KBS, TRY 1.2 MB TABLE FIRST
   982                              <1> 
   983                              <1> USE_EST2:
   984 00003D8E B002                <1> 	MOV	AL,02			; DRIVE TYPE 2 (1.2MB)
   985 00003D90 E88C010000          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL
   986 00003D95 8A4B04              <1>         MOV     CL, [eBX+MD.SEC_TRK]    ; GET SECTOR/TRACK
   987 00003D98 8A6B0B              <1>         MOV     CH, [eBX+MD.MAX_TRK]    ; GET MAX. TRACK NUMBER
   988 00003D9B 80FC40              <1> 	CMP	AH,RATE_300		; RATE 300 ?
   989 00003D9E 7496                <1> 	JZ	short STO_CX		; MUST BE 1.2MB DRIVE
   990 00003DA0 EB87                <1> 	JMP	SHORT PARM144		; ELSE, IT IS 1.44MB DRIVE 
   991                              <1> 
   992                              <1> ; 30/08/2020
   993                              <1> 
   994                              <1> ;-------------------------------------------------------------------------------
   995                              <1> ; DISK_TYPE (AH = 15H)	
   996                              <1> ;	THIS ROUTINE RETURNS THE TYPE OF MEDIA INSTALLED.
   997                              <1> ;
   998                              <1> ;  ON ENTRY:	DI = DRIVE #
   999                              <1> ;
  1000                              <1> ;  ON EXIT:	AH = DRIVE TYPE, CY=0
  1001                              <1> ;-------------------------------------------------------------------------------
  1002                              <1> DSK_TYPE:
  1003 00003DA2 E8EE010000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
  1004 00003DA7 8A87[155F0100]      <1> 	MOV	AL,[DSK_STATE+eDI]	; GET PRESENT STATE INFORMATION
  1005 00003DAD 08C0                <1> 	OR	AL,AL			; CHECK FOR NO DRIVE
  1006 00003DAF 7418                <1> 	JZ	short NO_DRV
  1007 00003DB1 B401                <1> 	MOV	AH,NOCHGLN		; NO CHANGE LINE FOR 40 TRACK DRIVE
  1008 00003DB3 A801                <1> 	TEST	AL,TRK_CAPA		; IS THIS DRIVE AN 80 TRACK DRIVE?
  1009 00003DB5 7402                <1> 	JZ	short DT_BACK		; IF NO JUMP
  1010 00003DB7 B402                <1> 	MOV	AH,CHGLN		; CHANGE LINE FOR 80 TRACK DRIVE
  1011                              <1> DT_BACK:
  1012 00003DB9 6650                <1> 	PUSH	AX			; SAVE RETURN VALUE
  1013 00003DBB E806020000          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  1014 00003DC0 6658                <1> 	POP	AX			; RESTORE RETURN VALUE
  1015 00003DC2 F8                  <1> 	CLC				; NO ERROR
  1016 00003DC3 6689F3              <1> 	MOV	BX,SI			; GET SAVED AL TO BL
  1017 00003DC6 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
  1018 00003DC8 C3                  <1> 	RETn
  1019                              <1> NO_DRV:	
  1020                              <1> 	;XOR	AH,AH			; NO DRIVE PRESENT OR UNKNOWN
  1021                              <1> 	;JMP	SHORT DT_BACK
  1022                              <1> 	
  1023                              <1> 	; 30/08/2020
  1024 00003DC9 E8F8010000          <1> 	call	XLAT_OLD
  1025 00003DCE 29C0                <1> 	sub	eax, eax
  1026 00003DD0 F9                  <1> 	stc	; cf = 1 -> drive not ready, ah = 0 (disk type = 0)
  1027 00003DD1 C3                  <1> 	retn
  1028                              <1> 
  1029                              <1> ;-------------------------------------------------------------------------------
  1030                              <1> ; DISK_CHANGE	(AH = 16H)
  1031                              <1> ;	THIS ROUTINE RETURNS THE STATE OF THE DISK CHANGE LINE.
  1032                              <1> ;
  1033                              <1> ; ON ENTRY:	DI = DRIVE #
  1034                              <1> ;
  1035                              <1> ; ON EXIT:	AH = @DSKETTE_STATUS
  1036                              <1> ;		     00 - DISK CHANGE LINE INACTIVE, CY = 0
  1037                              <1> ;		     06 - DISK CHANGE LINE ACTIVE, CY = 1
  1038                              <1> ;-------------------------------------------------------------------------------
  1039                              <1> DSK_CHANGE:
  1040 00003DD2 E8BE010000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
  1041 00003DD7 8A87[155F0100]      <1> 	MOV	AL, [DSK_STATE+eDI]	; GET MEDIA STATE INFORMATION
  1042 00003DDD 08C0                <1> 	OR	AL,AL			; DRIVE PRESENT ?
  1043 00003DDF 7422                <1> 	JZ	short DC_NON		; JUMP IF NO DRIVE
  1044 00003DE1 A801                <1> 	TEST	AL,TRK_CAPA		; 80 TRACK DRIVE ?
  1045 00003DE3 7407                <1> 	JZ	short SETIT		; IF SO , CHECK CHANGE LINE
  1046                              <1> DC0:
  1047 00003DE5 E88D0A0000          <1>         CALL    READ_DSKCHNG            ; GO CHECK STATE OF DISK CHANGE LINE
  1048 00003DEA 7407                <1> 	JZ	short FINIS		; CHANGE LINE NOT ACTIVE
  1049                              <1> 
  1050 00003DEC C605[085F0100]06    <1> SETIT:	MOV	byte [DSKETTE_STATUS], MEDIA_CHANGE ; INDICATE MEDIA REMOVED
  1051                              <1> 
  1052 00003DF3 E8CE010000          <1> FINIS:	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  1053 00003DF8 E808070000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
  1054 00003DFD 6689F3              <1> 	MOV	BX,SI			; GET SAVED AL TO BL
  1055 00003E00 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
  1056 00003E02 C3                  <1> 	RETn
  1057                              <1> DC_NON:
  1058 00003E03 800D[085F0100]80    <1> 	OR	byte [DSKETTE_STATUS], TIME_OUT ; SET TIMEOUT, NO DRIVE
  1059 00003E0A EBE7                <1> 	JMP	SHORT FINIS
  1060                              <1> 
  1061                              <1> ;-------------------------------------------------------------------------------
  1062                              <1> ; FORMAT_SET	(AH = 17H)
  1063                              <1> ;	THIS ROUTINE IS USED TO ESTABLISH THE TYPE OF MEDIA TO BE USED
  1064                              <1> ;	FOR THE FOLLOWING FORMAT OPERATION.
  1065                              <1> ;
  1066                              <1> ; ON ENTRY:	SI LOW = DASD TYPE FOR FORMAT
  1067                              <1> ;		DI     = DRIVE #
  1068                              <1> ;
  1069                              <1> ; ON EXIT:	@DSKETTE_STATUS REFLECTS STATUS
  1070                              <1> ;		AH = @DSKETTE_STATUS
  1071                              <1> ;		CY = 1 IF ERROR
  1072                              <1> ;-------------------------------------------------------------------------------
  1073                              <1> FORMAT_SET:
  1074 00003E0C E884010000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
  1075 00003E11 6656                <1> 	PUSH	SI			; SAVE DASD TYPE
  1076 00003E13 6689F0              <1> 	MOV	AX,SI			; AH = ? , AL , DASD TYPE
  1077 00003E16 30E4                <1> 	XOR	AH,AH			; AH , 0 , AL , DASD TYPE
  1078 00003E18 6689C6              <1> 	MOV	SI,AX			; SI = DASD TYPE
  1079 00003E1B 80A7[155F0100]0F    <1> 	AND	byte [DSK_STATE+eDI], ~(MED_DET+DBL_STEP+RATE_MSK) ; CLEAR STATE
  1080 00003E22 664E                <1> 	DEC	SI			; CHECK FOR 320/360K MEDIA & DRIVE
  1081 00003E24 7509                <1> 	JNZ	short NOT_320		; BYPASS IF NOT
  1082 00003E26 808F[155F0100]90    <1> 	OR	byte [DSK_STATE+eDI], MED_DET+RATE_250 ; SET TO 320/360
  1083 00003E2D EB48                <1> 	JMP	SHORT S0
  1084                              <1> 
  1085                              <1> NOT_320:
  1086 00003E2F E8B6030000          <1> 	CALL	MED_CHANGE		; CHECK FOR TIME_OUT
  1087 00003E34 803D[085F0100]80    <1> 	CMP	byte [DSKETTE_STATUS], TIME_OUT
  1088 00003E3B 743A                <1> 	JZ	short S0		; IF TIME OUT TELL CALLER
  1089                              <1> S3:
  1090 00003E3D 664E                <1> 	DEC	SI			; CHECK FOR 320/360K IN 1.2M DRIVE
  1091 00003E3F 7509                <1> 	JNZ	short NOT_320_12	; BYPASS IF NOT
  1092 00003E41 808F[155F0100]70    <1> 	OR	byte [DSK_STATE+eDI], MED_DET+DBL_STEP+RATE_300 ; SET STATE
  1093 00003E48 EB2D                <1> 	JMP	SHORT S0
  1094                              <1> 
  1095                              <1> NOT_320_12:
  1096 00003E4A 664E                <1> 	DEC	SI			; CHECK FOR 1.2M MEDIA IN 1.2M DRIVE
  1097 00003E4C 7509                <1> 	JNZ	short NOT_12		; BYPASS IF NOT
  1098 00003E4E 808F[155F0100]10    <1> 	OR	byte [DSK_STATE+eDI], MED_DET+RATE_500 ; SET STATE VARIABLE
  1099 00003E55 EB20                <1> 	JMP	SHORT S0		; RETURN TO CALLER
  1100                              <1> 
  1101                              <1> NOT_12:	
  1102 00003E57 664E                <1> 	DEC	SI			; CHECK FOR SET DASD TYPE 04
  1103 00003E59 752B                <1> 	JNZ	short FS_ERR		; BAD COMMAND EXIT IF NOT VALID TYPE
  1104                              <1> 
  1105 00003E5B F687[155F0100]04    <1> 	TEST	byte [DSK_STATE+eDI], DRV_DET ; DRIVE DETERMINED ?
  1106 00003E62 740B                <1> 	JZ	short ASSUME		; IF STILL NOT DETERMINED ASSUME
  1107 00003E64 B050                <1> 	MOV	AL,MED_DET+RATE_300
  1108 00003E66 F687[155F0100]02    <1>         TEST    byte [DSK_STATE+eDI], FMT_CAPA ; MULTIPLE FORMAT CAPABILITY ?
  1109 00003E6D 7502                <1> 	JNZ	short OR_IT_IN		; IF 1.2 M THEN DATA RATE 300
  1110                              <1> 
  1111                              <1> ASSUME:
  1112 00003E6F B090                <1> 	MOV	AL,MED_DET+RATE_250	; SET UP
  1113                              <1> 
  1114                              <1> OR_IT_IN:
  1115 00003E71 0887[155F0100]      <1> 	OR	[DSK_STATE+eDI], AL	; OR IN THE CORRECT STATE
  1116                              <1> S0:
  1117 00003E77 E84A010000          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  1118 00003E7C E884060000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
  1119 00003E81 665B                <1> 	POP	BX			; GET SAVED AL TO BL
  1120 00003E83 88D8                <1> 	MOV	AL,BL			; PUT BACK FOR RETURN
  1121 00003E85 C3                  <1> 	RETn
  1122                              <1> 
  1123                              <1> FS_ERR:
  1124 00003E86 C605[085F0100]01    <1> 	MOV	byte [DSKETTE_STATUS], BAD_CMD ; UNKNOWN STATE,BAD COMMAND
  1125 00003E8D EBE8                <1> 	JMP	SHORT S0
  1126                              <1> 
  1127                              <1> ;-------------------------------------------------------------------------------
  1128                              <1> ; SET_MEDIA	(AH = 18H)
  1129                              <1> ;	THIS ROUTINE SETS THE TYPE OF MEDIA AND DATA RATE 
  1130                              <1> ;	TO BE USED FOR THE FOLLOWING FORMAT OPERATION.
  1131                              <1> ;
  1132                              <1> ; ON ENTRY:
  1133                              <1> ;	[BP]	= SECTOR PER TRACK
  1134                              <1> ;	[BP+1]	= TRACK #
  1135                              <1> ;	DI	= DRIVE #
  1136                              <1> ;
  1137                              <1> ; ON EXIT:
  1138                              <1> ;	@DSKETTE_STATUS REFLECTS STATUS
  1139                              <1> ;	IF NO ERROR:
  1140                              <1> ;		AH = 0
  1141                              <1> ;		CY = 0
  1142                              <1> ;		ES = SEGMENT OF MEDIA/DRIVE PARAMETER TABLE
  1143                              <1> ;		DI/[BP+6] = OFFSET OF MEDIA/DRIVE PARAMETER TABLE
  1144                              <1> ;	IF ERROR:	
  1145                              <1> ;		AH = @DSKETTE_STATUS
  1146                              <1> ;		CY = 1
  1147                              <1> ;-------------------------------------------------------------------------------
  1148                              <1> SET_MEDIA:
  1149 00003E8F E801010000          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
  1150 00003E94 F687[155F0100]01    <1>         TEST    byte [DSK_STATE+eDI], TRK_CAPA ; CHECK FOR CHANGE LINE AVAILABLE
  1151 00003E9B 7415                <1> 	JZ	short SM_CMOS		; JUMP IF 40 TRACK DRIVE
  1152 00003E9D E848030000          <1> 	CALL	MED_CHANGE		; RESET CHANGE LINE
  1153 00003EA2 803D[085F0100]80    <1> 	CMP	byte [DSKETTE_STATUS], TIME_OUT ; IF TIME OUT TELL CALLER
  1154 00003EA9 746B                <1> 	JE	short SM_RTN
  1155 00003EAB C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS], 0 ; CLEAR STATUS
  1156                              <1> SM_CMOS:
  1157 00003EB2 E819070000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN (AL)
  1158                              <1> 	;;20/02/2015
  1159                              <1> 	;;JC	short MD_NOT_FND	; ERROR IN CMOS
  1160                              <1> 	;;OR	AL,AL			; TEST FOR NO DRIVE
  1161 00003EB7 745D                <1> 	JZ	short SM_RTN		; RETURN IF SO
  1162 00003EB9 E863000000          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL
  1163 00003EBE 7231                <1> 	JC	short MD_NOT_FND	; TYPE NOT IN TABLE (BAD CMOS)
  1164 00003EC0 57                  <1> 	PUSH	eDI			; SAVE REG.
  1165 00003EC1 31DB                <1> 	XOR	eBX,eBX			; BX = INDEX TO DR. TYPE TABLE
  1166 00003EC3 B906000000          <1> 	MOV	eCX,DR_CNT		; CX = LOOP COUNT
  1167                              <1> DR_SEARCH:
  1168 00003EC8 8AA3[28640000]      <1> 	MOV	AH, [DR_TYPE+eBX]	; GET DRIVE TYPE
  1169 00003ECE 80E47F              <1> 	AND	AH,BIT7OFF		; MASK OUT MSB
  1170 00003ED1 38E0                <1> 	CMP	AL,AH			; DRIVE TYPE MATCH ?
  1171 00003ED3 7516                <1> 	JNE	short NXT_MD		; NO, CHECK NEXT DRIVE TYPE
  1172                              <1> DR_FND:
  1173 00003ED5 8BBB[29640000]      <1> 	MOV	eDI, [DR_TYPE+eBX+1] 	; DI = MEDIA/DRIVE PARAM TABLE
  1174                              <1> MD_SEARCH:
  1175 00003EDB 8A6704              <1>         MOV     AH, [eDI+MD.SEC_TRK]    ; GET SECTOR/TRACK
  1176 00003EDE 386500              <1> 	CMP	[eBP],AH		; MATCH?
  1177 00003EE1 7508                <1> 	JNE	short NXT_MD		; NO, CHECK NEXT MEDIA
  1178 00003EE3 8A670B              <1>         MOV     AH, [eDI+MD.MAX_TRK]    ; GET MAX. TRACK #
  1179 00003EE6 386501              <1> 	CMP 	[eBP+1],AH		; MATCH?
  1180 00003EE9 740F                <1> 	JE	short MD_FND		; YES, GO GET RATE
  1181                              <1> NXT_MD:
  1182                              <1> 	;ADD	BX,3			; CHECK NEXT DRIVE TYPE
  1183 00003EEB 83C305              <1>         add	ebx, 5 ; 18/02/2015
  1184 00003EEE E2D8                <1> 	LOOP    DR_SEARCH
  1185 00003EF0 5F                  <1> 	POP	eDI			; RESTORE REG.
  1186                              <1> MD_NOT_FND:
  1187 00003EF1 C605[085F0100]0C    <1> 	MOV	byte [DSKETTE_STATUS], MED_NOT_FND ; ERROR, MEDIA TYPE NOT FOUND
  1188 00003EF8 EB1C                <1> 	JMP	SHORT SM_RTN		; RETURN
  1189                              <1> MD_FND:
  1190 00003EFA 8A470C              <1>         MOV     AL, [eDI+MD.RATE]       ; GET RATE
  1191 00003EFD 3C40                <1> 	CMP	AL,RATE_300		; DOUBLE STEP REQUIRED FOR RATE 300
  1192 00003EFF 7502                <1> 	JNE	short MD_SET
  1193 00003F01 0C20                <1> 	OR	AL,DBL_STEP
  1194                              <1> MD_SET:
  1195                              <1> 	;MOV	[BP+6],DI		; SAVE TABLE POINTER IN STACK
  1196 00003F03 897D0C              <1> 	mov	[ebp+12], edi ; 18/02/2015
  1197 00003F06 0C10                <1> 	OR	AL,MED_DET		; SET MEDIA ESTABLISHED
  1198 00003F08 5F                  <1> 	POP	eDI
  1199 00003F09 80A7[155F0100]0F    <1> 	AND	byte [DSK_STATE+eDI], ~(MED_DET+DBL_STEP+RATE_MSK) ; CLEAR STATE
  1200 00003F10 0887[155F0100]      <1> 	OR	[DSK_STATE+eDI], AL
  1201                              <1> 	;MOV	AX, CS			; SEGMENT OF MEDIA/DRIVE PARAMETER TABLE
  1202                              <1> 	;MOV	ES, AX			; ES IS SEGMENT OF TABLE
  1203                              <1> SM_RTN:
  1204 00003F16 E8AB000000          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  1205 00003F1B E8E5050000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
  1206 00003F20 C3                  <1> 	RETn
  1207                              <1> 
  1208                              <1> ;----------------------------------------------------------------
  1209                              <1> ; DR_TYPE_CHECK							:
  1210                              <1> ;	CHECK IF THE GIVEN DRIVE TYPE IN REGISTER (AL)		:
  1211                              <1> ;	IS SUPPORTED IN BIOS DRIVE TYPE TABLE			:
  1212                              <1> ; ON ENTRY:							:
  1213                              <1> ;	AL = DRIVE TYPE						:
  1214                              <1> ; ON EXIT:							:
  1215                              <1> ;	CS = SEGMENT MEDIA/DRIVE PARAMETER TABLE (CODE)		:
  1216                              <1> ;	CY = 0 	DRIVE TYPE SUPPORTED				:
  1217                              <1> ;	     BX = OFFSET TO MEDIA/DRIVE PARAMETER TABLE		:
  1218                              <1> ;	CY = 1	DRIVE TYPE NOT SUPPORTED 			:
  1219                              <1> ; REGISTERS ALTERED: eBX						:
  1220                              <1> ;----------------------------------------------------------------		
  1221                              <1> DR_TYPE_CHECK:
  1222 00003F21 6650                <1> 	PUSH	AX			
  1223 00003F23 51                  <1> 	PUSH	eCX
  1224 00003F24 31DB                <1> 	XOR	eBX,eBX			; BX = INDEX TO DR_TYPE TABLE
  1225 00003F26 B906000000          <1> 	MOV	eCX,DR_CNT		; CX = LOOP COUNT
  1226                              <1> TYPE_CHK:	
  1227 00003F2B 8AA3[28640000]      <1> 	MOV	AH,[DR_TYPE+eBX]	; GET DRIVE TYPE
  1228 00003F31 38E0                <1> 	CMP	AL,AH			; DRIVE TYPE MATCH?
  1229 00003F33 740D                <1> 	JE	short DR_TYPE_VALID	; YES, RETURN WITH CARRY RESET
  1230                              <1> 	;ADD	BX,3			; CHECK NEXT DRIVE TYPE
  1231 00003F35 83C305              <1>         add	ebx, 5	; 16/02/2015 (32 bit address modification)
  1232 00003F38 E2F1                <1> 	LOOP    TYPE_CHK
  1233                              <1> 	;
  1234 00003F3A BB[87640000]        <1> 	mov	ebx, MD_TBL6		; 1.44MB fd parameter table
  1235                              <1> 					; Default for GET_PARM (11/12/2014)
  1236                              <1> 	;
  1237 00003F3F F9                  <1> 	STC				; DRIVE TYPE NOT FOUND IN TABLE
  1238 00003F40 EB06                <1> 	JMP	SHORT TYPE_RTN
  1239                              <1> DR_TYPE_VALID:
  1240 00003F42 8B9B[29640000]      <1> 	MOV	eBX,[DR_TYPE+eBX+1] 	; BX = MEDIA TABLE
  1241                              <1> TYPE_RTN:
  1242 00003F48 59                  <1> 	POP	eCX
  1243 00003F49 6658                <1> 	POP	AX
  1244 00003F4B C3                  <1> 	RETn	
  1245                              <1> 		
  1246                              <1> ;----------------------------------------------------------------
  1247                              <1> ; SEND_SPEC							:
  1248                              <1> ;	SEND THE SPECIFY COMMAND TO CONTROLLER USING DATA FROM	:
  1249                              <1> ;	THE DRIVE PARAMETER TABLE POINTED BY @DISK_POINTER	:
  1250                              <1> ; ON ENTRY:	@DISK_POINTER = DRIVE PARAMETER TABLE		:
  1251                              <1> ; ON EXIT:	NONE						:	
  1252                              <1> ; REGISTERS ALTERED: CX, DX					:
  1253                              <1> ;----------------------------------------------------------------		
  1254                              <1> SEND_SPEC:
  1255 00003F4C 50                  <1> 	PUSH	eAX			; SAVE AX
  1256 00003F4D B8[733F0000]        <1> 	MOV	eAX, SPECBAC		; LOAD ERROR ADDRESS
  1257 00003F52 50                  <1> 	PUSH	eAX			; PUSH NEC_OUT ERROR RETURN
  1258 00003F53 B403                <1> 	MOV	AH,03H			; SPECIFY COMMAND
  1259 00003F55 E885070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1260 00003F5A 28D2                <1> 	SUB	DL,DL			; FIRST SPECIFY BYTE
  1261 00003F5C E878060000          <1> 	CALL	GET_PARM		; GET PARAMETER TO AH
  1262 00003F61 E879070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1263 00003F66 B201                <1> 	MOV	DL,1			; SECOND SPECIFY BYTE
  1264 00003F68 E86C060000          <1> 	CALL	GET_PARM		; GET PARAMETER TO AH
  1265 00003F6D E86D070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1266 00003F72 58                  <1> 	POP	eAX			; POP ERROR RETURN
  1267                              <1> SPECBAC:
  1268 00003F73 58                  <1> 	POP	eAX			; RESTORE ORIGINAL AX VALUE
  1269 00003F74 C3                  <1> 	RETn
  1270                              <1> 
  1271                              <1> ;----------------------------------------------------------------
  1272                              <1> ; SEND_SPEC_MD							:
  1273                              <1> ;	SEND THE SPECIFY COMMAND TO CONTROLLER USING DATA FROM	:
  1274                              <1> ;	THE MEDIA/DRIVE PARAMETER TABLE POINTED BY (CS:BX)	:
  1275                              <1> ; ON ENTRY:	CS:BX = MEDIA/DRIVE PARAMETER TABLE		:
  1276                              <1> ; ON EXIT:	NONE						:	
  1277                              <1> ; REGISTERS ALTERED: AX						:
  1278                              <1> ;----------------------------------------------------------------		
  1279                              <1> SEND_SPEC_MD:
  1280 00003F75 50                  <1> 	PUSH	eAX			; SAVE RATE DATA
  1281 00003F76 B8[933F0000]        <1> 	MOV	eAX, SPEC_ESBAC		; LOAD ERROR ADDRESS
  1282 00003F7B 50                  <1> 	PUSH	eAX			; PUSH NEC_OUT ERROR RETURN
  1283 00003F7C B403                <1> 	MOV	AH,03H			; SPECIFY COMMAND
  1284 00003F7E E85C070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1285 00003F83 8A23                <1>         MOV     AH, [eBX+MD.SPEC1]      ; GET 1ST SPECIFY BYTE
  1286 00003F85 E855070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1287 00003F8A 8A6301              <1>         MOV     AH, [eBX+MD.SPEC2]      ; GET SECOND SPECIFY BYTE
  1288 00003F8D E84D070000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE COMMAND
  1289 00003F92 58                  <1> 	POP	eAX			; POP ERROR RETURN
  1290                              <1> SPEC_ESBAC:
  1291 00003F93 58                  <1> 	POP	eAX			; RESTORE ORIGINAL AX VALUE
  1292 00003F94 C3                  <1> 	RETn
  1293                              <1> 
  1294                              <1> ;-------------------------------------------------------------------------------
  1295                              <1> ; XLAT_NEW  
  1296                              <1> ;	TRANSLATES DISKETTE STATE LOCATIONS FROM COMPATIBLE
  1297                              <1> ;	MODE TO NEW ARCHITECTURE.
  1298                              <1> ;
  1299                              <1> ; ON ENTRY:	DI = DRIVE #
  1300                              <1> ;-------------------------------------------------------------------------------
  1301                              <1> XLAT_NEW:
  1302 00003F95 83FF01              <1> 	CMP	eDI,1				; VALID DRIVE
  1303 00003F98 7725                <1> 	JA	short XN_OUT			; IF INVALID BACK
  1304 00003F9A 80BF[155F0100]00    <1> 	CMP	byte [DSK_STATE+eDI], 0		; NO DRIVE ?
  1305 00003FA1 741D                <1> 	JZ	short DO_DET			; IF NO DRIVE ATTEMPT DETERMINE
  1306 00003FA3 6689F9              <1> 	MOV	CX,DI				; CX = DRIVE NUMBER
  1307 00003FA6 C0E102              <1> 	SHL	CL,2				; CL = SHIFT COUNT, A=0, B=4
  1308 00003FA9 A0[145F0100]        <1> 	MOV	AL, [HF_CNTRL]			; DRIVE INFORMATION
  1309 00003FAE D2C8                <1> 	ROR	AL,CL				; TO LOW NIBBLE
  1310 00003FB0 2407                <1> 	AND	AL,DRV_DET+FMT_CAPA+TRK_CAPA	; KEEP DRIVE BITS
  1311 00003FB2 80A7[155F0100]F8    <1>         AND     byte [DSK_STATE+eDI], ~(DRV_DET+FMT_CAPA+TRK_CAPA)
  1312 00003FB9 0887[155F0100]      <1> 	OR	[DSK_STATE+eDI], AL		; UPDATE DRIVE STATE
  1313                              <1> XN_OUT:
  1314 00003FBF C3                  <1> 	RETn
  1315                              <1> DO_DET:
  1316 00003FC0 E8BF080000          <1> 	CALL	DRIVE_DET			; TRY TO DETERMINE
  1317 00003FC5 C3                  <1> 	RETn
  1318                              <1> 
  1319                              <1> ;-------------------------------------------------------------------------------
  1320                              <1> ; XLAT_OLD 
  1321                              <1> ;	TRANSLATES DISKETTE STATE LOCATIONS FROM NEW
  1322                              <1> ;	ARCHITECTURE TO COMPATIBLE MODE.
  1323                              <1> ;
  1324                              <1> ; ON ENTRY:	DI = DRIVE
  1325                              <1> ;-------------------------------------------------------------------------------
  1326                              <1> XLAT_OLD:
  1327 00003FC6 83FF01              <1> 	CMP	eDI,1			; VALID DRIVE ?
  1328                              <1>         ;JA     short XO_OUT            ; IF INVALID BACK
  1329 00003FC9 0F8786000000        <1>         ja      XO_OUT
  1330 00003FCF 80BF[155F0100]00    <1>         CMP	byte [DSK_STATE+eDI],0	; NO DRIVE ?
  1331 00003FD6 747D                <1> 	JZ	short XO_OUT		; IF NO DRIVE TRANSLATE DONE
  1332                              <1> 
  1333                              <1> ;-----	TEST FOR SAVED DRIVE INFORMATION ALREADY SET
  1334                              <1> 
  1335 00003FD8 6689F9              <1> 	MOV	CX,DI			; CX = DRIVE NUMBER
  1336 00003FDB C0E102              <1> 	SHL	CL,2			; CL = SHIFT COUNT, A=0, B=4
  1337 00003FDE B402                <1> 	MOV	AH,FMT_CAPA		; LOAD MULTIPLE DATA RATE BIT MASK
  1338 00003FE0 D2CC                <1> 	ROR	AH,CL			; ROTATE BY MASK
  1339 00003FE2 8425[145F0100]      <1> 	TEST	[HF_CNTRL], AH		; MULTIPLE-DATA RATE DETERMINED ?
  1340 00003FE8 751C                <1> 	JNZ	short SAVE_SET		; IF SO, NO NEED TO RE-SAVE
  1341                              <1> 
  1342                              <1> ;-----	ERASE DRIVE BITS IN @HF_CNTRL FOR THIS DRIVE
  1343                              <1> 
  1344 00003FEA B407                <1> 	MOV	AH,DRV_DET+FMT_CAPA+TRK_CAPA ; MASK TO KEEP
  1345 00003FEC D2CC                <1> 	ROR	AH,CL			; FIX MASK TO KEEP
  1346 00003FEE F6D4                <1> 	NOT	AH			; TRANSLATE MASK
  1347 00003FF0 2025[145F0100]      <1> 	AND	[HF_CNTRL], AH		; KEEP BITS FROM OTHER DRIVE INTACT
  1348                              <1> 
  1349                              <1> ;-----	ACCESS CURRENT DRIVE BITS AND STORE IN @HF_CNTRL
  1350                              <1> 
  1351 00003FF6 8A87[155F0100]      <1> 	MOV	AL, [DSK_STATE+eDI]	; ACCESS STATE
  1352 00003FFC 2407                <1> 	AND	AL,DRV_DET+FMT_CAPA+TRK_CAPA ; KEEP DRIVE BITS
  1353 00003FFE D2C8                <1> 	ROR	AL,CL			; FIX FOR THIS DRIVE
  1354 00004000 0805[145F0100]      <1> 	OR	[HF_CNTRL], AL		; UPDATE SAVED DRIVE STATE
  1355                              <1> 
  1356                              <1> ;-----	TRANSLATE TO COMPATIBILITY MODE
  1357                              <1> 
  1358                              <1> SAVE_SET:
  1359 00004006 8AA7[155F0100]      <1> 	MOV	AH, [DSK_STATE+eDI]	; ACCESS STATE
  1360 0000400C 88E7                <1> 	MOV	BH,AH			; TO BH FOR LATER
  1361 0000400E 80E4C0              <1> 	AND	AH,RATE_MSK		; KEEP ONLY RATE
  1362 00004011 80FC00              <1> 	CMP	AH,RATE_500		; RATE 500 ?
  1363 00004014 7410                <1> 	JZ	short CHK_144		; YES 1.2/1.2 OR 1.44/1.44
  1364 00004016 B001                <1> 	MOV	AL,M3D1U		; AL = 360 IN 1.2 UNESTABLISHED
  1365 00004018 80FC40              <1> 	CMP	AH,RATE_300		; RATE 300 ?
  1366 0000401B 7518                <1> 	JNZ	short CHK_250		; NO, 360/360, 720/720 OR 720/1.44
  1367 0000401D F6C720              <1> 	TEST	BH,DBL_STEP		; CHECK FOR DOUBLE STEP
  1368 00004020 751F                <1> 	JNZ	short TST_DET		; MUST BE 360 IN 1.2
  1369                              <1> UNKNO:
  1370 00004022 B007                <1> 	MOV	AL,MED_UNK		; NONE OF THE ABOVE
  1371 00004024 EB22                <1> 	JMP	SHORT AL_SET		; PROCESS COMPLETE
  1372                              <1> CHK_144:
  1373 00004026 E8A5050000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN (AL)
  1374                              <1> 	;;20/02/2015
  1375                              <1> 	;;JC	short UNKNO		; ERROR, SET 'NONE OF ABOVE'
  1376 0000402B 74F5                <1> 	jz	short UNKNO ;; 20/02/2015
  1377 0000402D 3C02                <1> 	CMP	AL,2			; 1.2MB DRIVE ?
  1378 0000402F 75F1                <1> 	JNE	short UNKNO		; NO, GO SET 'NONE OF ABOVE'
  1379 00004031 B002                <1> 	MOV	AL,M1D1U		; AL = 1.2 IN 1.2 UNESTABLISHED
  1380 00004033 EB0C                <1> 	JMP	SHORT TST_DET
  1381                              <1> CHK_250:
  1382 00004035 B000                <1> 	MOV	AL,M3D3U		; AL = 360 IN 360 UNESTABLISHED
  1383 00004037 80FC80              <1> 	CMP	AH,RATE_250		; RATE 250 ?
  1384 0000403A 75E6                <1> 	JNZ	short UNKNO		; IF SO FALL IHRU
  1385 0000403C F6C701              <1> 	TEST	BH,TRK_CAPA		; 80 TRACK CAPABILITY ?
  1386 0000403F 75E1                <1> 	JNZ	short UNKNO		; IF SO JUMP, FALL THRU TEST DET
  1387                              <1> TST_DET:
  1388 00004041 F6C710              <1> 	TEST	BH,MED_DET		; DETERMINED ?
  1389 00004044 7402                <1> 	JZ	short AL_SET		; IF NOT THEN SET
  1390 00004046 0403                <1> 	ADD	AL,3			; MAKE DETERMINED/ESTABLISHED
  1391                              <1> AL_SET:
  1392 00004048 80A7[155F0100]F8    <1> 	AND	byte [DSK_STATE+eDI], ~(DRV_DET+FMT_CAPA+TRK_CAPA) ; CLEAR DRIVE
  1393 0000404F 0887[155F0100]      <1> 	OR	[DSK_STATE+eDI], AL	; REPLACE WITH COMPATIBLE MODE
  1394                              <1> XO_OUT:
  1395 00004055 C3                  <1> 	RETn
  1396                              <1> 
  1397                              <1> ;-------------------------------------------------------------------------------
  1398                              <1> ; RD_WR_VF
  1399                              <1> ;	COMMON READ, WRITE AND VERIFY: 
  1400                              <1> ;	MAIN LOOP FOR STATE RETRIES.
  1401                              <1> ;
  1402                              <1> ; ON ENTRY:	AH = READ/WRITE/VERIFY NEC PARAMETER
  1403                              <1> ;		AL = READ/WRITE/VERIFY DMA PARAMETER
  1404                              <1> ;
  1405                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  1406                              <1> ;-------------------------------------------------------------------------------
  1407                              <1> RD_WR_VF:
  1408 00004056 6650                <1> 	PUSH	AX			; SAVE DMA, NEC PARAMETERS
  1409 00004058 E838FFFFFF          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH.
  1410 0000405D E8F3000000          <1> 	CALL	SETUP_STATE		; INITIALIZE START AND END RATE
  1411 00004062 6658                <1> 	POP	AX			; RESTORE READ/WRITE/VERIFY
  1412                              <1> DO_AGAIN:
  1413 00004064 6650                <1> 	PUSH	AX			; SAVE READ/WRITE/VERIFY PARAMETER
  1414 00004066 E87F010000          <1> 	CALL	MED_CHANGE		; MEDIA CHANGE AND RESET IF CHANGED
  1415 0000406B 6658                <1> 	POP	AX			; RESTORE READ/WRITE/VERIFY
  1416 0000406D 0F82C9000000        <1>         JC      RWV_END                 ; MEDIA CHANGE ERROR OR TIME-OUT
  1417                              <1> RWV:
  1418 00004073 6650                <1> 	PUSH	AX			; SAVE READ/WRITE/VERIFY PARAMETER
  1419 00004075 8AB7[155F0100]      <1> 	MOV	DH, [DSK_STATE+eDI]	; GET RATE STATE OF THIS DRIVE
  1420 0000407B 80E6C0              <1> 	AND	DH,RATE_MSK		; KEEP ONLY RATE
  1421 0000407E E84D050000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN AL (AL)
  1422                              <1> 	;;20/02/2015
  1423                              <1> 	;;JC	short RWV_ASSUME	; ERROR IN CMOS
  1424 00004083 7451                <1> 	jz	short RWV_ASSUME ; 20/02/2015
  1425 00004085 3C01                <1> 	CMP	AL,1			; 40 TRACK DRIVE?
  1426 00004087 750D                <1> 	JNE	short RWV_1		; NO, BYPASS CMOS VALIDITY CHECK
  1427 00004089 F687[155F0100]01    <1> 	TEST	byte [DSK_STATE+eDI], TRK_CAPA ; CHECK FOR 40 TRACK DRIVE
  1428 00004090 7413                <1> 	JZ	short RWV_2		; YES, CMOS IS CORRECT
  1429 00004092 B002                <1> 	MOV	AL,2			; CHANGE TO 1.2M
  1430 00004094 EB0F                <1> 	JMP	SHORT RWV_2
  1431                              <1> RWV_1:
  1432 00004096 720D                <1> 	JB	short RWV_2		; NO DRIVE SPECIFIED, CONTINUE
  1433 00004098 F687[155F0100]01    <1> 	TEST    byte [DSK_STATE+eDI], TRK_CAPA ; IS IT REALLY 40 TRACK?
  1434 0000409F 7504                <1> 	JNZ	short RWV_2		; NO, 80 TRACK
  1435 000040A1 B001                <1> 	MOV	AL,1			; IT IS 40 TRACK, FIX CMOS VALUE
  1436 000040A3 EB04                <1> 	jmp	short rwv_3
  1437                              <1> RWV_2:
  1438 000040A5 08C0                <1> 	OR	AL,AL			; TEST FOR NO DRIVE
  1439 000040A7 742D                <1> 	JZ	short RWV_ASSUME	; ASSUME TYPE, USE MAX TRACK
  1440                              <1> rwv_3:
  1441 000040A9 E873FEFFFF          <1> 	CALL	DR_TYPE_CHECK		; RTN CS:BX = MEDIA/DRIVE PARAM TBL.
  1442 000040AE 7226                <1> 	JC	short RWV_ASSUME	; TYPE NOT IN TABLE (BAD CMOS)
  1443                              <1> 
  1444                              <1> ;-----	SEARCH FOR MEDIA/DRIVE PARAMETER TABLE
  1445                              <1> 
  1446 000040B0 57                  <1> 	PUSH	eDI			; SAVE DRIVE #
  1447 000040B1 31DB                <1> 	XOR	eBX,eBX			; BX = INDEX TO DR_TYPE TABLE
  1448 000040B3 B906000000          <1> 	MOV	eCX,DR_CNT		; CX = LOOP COUNT
  1449                              <1> RWV_DR_SEARCH:
  1450 000040B8 8AA3[28640000]      <1> 	MOV	AH, [DR_TYPE+eBX]	; GET DRIVE TYPE
  1451 000040BE 80E47F              <1> 	AND	AH,BIT7OFF		; MASK OUT MSB
  1452 000040C1 38E0                <1> 	CMP	AL,AH			; DRIVE TYPE MATCH?
  1453 000040C3 750B                <1> 	JNE	short RWV_NXT_MD	; NO, CHECK NEXT DRIVE TYPE
  1454                              <1> RWV_DR_FND:
  1455 000040C5 8BBB[29640000]      <1> 	MOV	eDI, [DR_TYPE+eBX+1] 	; DI = MEDIA/DRIVE PARAMETER TABLE
  1456                              <1> RWV_MD_SEARH:
  1457 000040CB 3A770C              <1>         CMP     DH, [eDI+MD.RATE]       ; MATCH?
  1458 000040CE 741B                <1> 	JE	short RWV_MD_FND	; YES, GO GET 1ST SPECIFY BYTE
  1459                              <1> RWV_NXT_MD:
  1460                              <1> 	;ADD	BX,3			; CHECK NEXT DRIVE TYPE
  1461 000040D0 83C305              <1> 	add	eBX, 5
  1462 000040D3 E2E3                <1> 	LOOP	RWV_DR_SEARCH
  1463 000040D5 5F                  <1> 	POP	eDI			; RESTORE DRIVE #
  1464                              <1> 
  1465                              <1> ;-----	ASSUME PRIMARY DRIVE IS INSTALLED AS SHIPPED
  1466                              <1> 
  1467                              <1> RWV_ASSUME:
  1468 000040D6 BB[46640000]        <1> 	MOV	eBX, MD_TBL1		; POINT TO 40 TRACK 250 KBS
  1469 000040DB F687[155F0100]01    <1> 	TEST 	byte [DSK_STATE+eDI], TRK_CAPA ; TEST FOR 80 TRACK
  1470 000040E2 740A                <1> 	JZ	short RWV_MD_FND1	; MUST BE 40 TRACK
  1471 000040E4 BB[60640000]        <1> 	MOV	eBX, MD_TBL3		; POINT TO 80 TRACK 500 KBS
  1472 000040E9 EB03                <1> 	JMP	short RWV_MD_FND1	; GO SPECIFY PARAMTERS
  1473                              <1> 
  1474                              <1> ;-----	CS:BX POINTS TO MEDIA/DRIVE PARAMETER TABLE
  1475                              <1> 	 			
  1476                              <1> RWV_MD_FND:
  1477 000040EB 89FB                <1> 	MOV	eBX,eDI			; BX = MEDIA/DRIVE PARAMETER TABLE
  1478 000040ED 5F                  <1> 	POP	eDI			; RESTORE DRIVE #
  1479                              <1> 	
  1480                              <1> ;-----	SEND THE SPECIFY COMMAND TO THE CONTROLLER
  1481                              <1> 
  1482                              <1> RWV_MD_FND1:
  1483 000040EE E882FEFFFF          <1> 	CALL	SEND_SPEC_MD
  1484 000040F3 E864010000          <1> 	CALL	CHK_LASTRATE		; ZF=1 ATTEMP RATE IS SAME AS LAST RATE
  1485 000040F8 7405                <1> 	JZ	short RWV_DBL		; YES,SKIP SEND RATE COMMAND
  1486 000040FA E83B010000          <1> 	CALL	SEND_RATE		; SEND DATA RATE TO NEC
  1487                              <1> RWV_DBL:
  1488 000040FF 53                  <1> 	PUSH	eBX			; SAVE MEDIA/DRIVE PARAM TBL ADDRESS
  1489 00004100 E822040000          <1> 	CALL	SETUP_DBL		; CHECK FOR DOUBLE STEP
  1490 00004105 5B                  <1> 	POP	eBX			; RESTORE ADDRESS
  1491 00004106 7226                <1> 	JC	short CHK_RET		; ERROR FROM READ ID, POSSIBLE RETRY
  1492 00004108 6658                <1> 	POP	AX			; RESTORE NEC, DMA COMMAND
  1493 0000410A 6650                <1> 	PUSH	AX			; SAVE NEC COMMAND
  1494 0000410C 53                  <1> 	PUSH	eBX			; SAVE MEDIA/DRIVE PARAM TBL ADDRESS
  1495 0000410D E861010000          <1> 	CALL	DMA_SETUP		; SET UP THE DMA
  1496 00004112 5B                  <1> 	POP	eBX 
  1497 00004113 6658                <1> 	POP	AX			; RESTORE NEC COMMAND
  1498 00004115 722F                <1> 	JC	short RWV_BAC		; CHECK FOR DMA BOUNDARY ERROR
  1499 00004117 6650                <1> 	PUSH	AX			; SAVE NEC COMMAND
  1500 00004119 53                  <1> 	PUSH	eBX			; SAVE MEDIA/DRIVE PARAM TBL ADDRESS
  1501 0000411A E83C020000          <1> 	CALL	NEC_INIT		; INITIALIZE NEC
  1502 0000411F 5B                  <1> 	POP	eBX			; RESTORE ADDRESS
  1503 00004120 720C                <1> 	JC	short CHK_RET		; ERROR - EXIT
  1504 00004122 E866020000          <1> 	CALL	RWV_COM			; OP CODE COMMON TO READ/WRITE/VERIFY
  1505 00004127 7205                <1> 	JC	short CHK_RET		; ERROR - EXIT
  1506 00004129 E8AB020000          <1> 	CALL	NEC_TERM		; TERMINATE, GET STATUS, ETC.
  1507                              <1> CHK_RET:
  1508 0000412E E84A030000          <1> 	CALL	RETRY			; CHECK FOR, SETUP RETRY
  1509 00004133 6658                <1> 	POP	AX			; RESTORE READ/WRITE/VERIFY PARAMETER
  1510 00004135 7305                <1> 	JNC	short RWV_END		; CY = 0 NO RETRY
  1511 00004137 E928FFFFFF          <1>         JMP     DO_AGAIN                ; CY = 1 MEANS RETRY
  1512                              <1> RWV_END:
  1513 0000413C E8F4020000          <1> 	CALL	DSTATE			; ESTABLISH STATE IF SUCCESSFUL
  1514 00004141 E887030000          <1> 	CALL	NUM_TRANS		; AL = NUMBER TRANSFERRED
  1515                              <1> RWV_BAC:				; BAD DMA ERROR ENTRY
  1516 00004146 6650                <1> 	PUSH	AX			; SAVE NUMBER TRANSFERRED
  1517 00004148 E879FEFFFF          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  1518 0000414D 6658                <1> 	POP	AX			; RESTORE NUMBER TRANSFERRED
  1519 0000414F E8B1030000          <1> 	CALL	SETUP_END		; VARIOUS CLEANUPS
  1520 00004154 C3                  <1> 	RETn
  1521                              <1> 
  1522                              <1> ;-------------------------------------------------------------------------------
  1523                              <1> ; SETUP_STATE:	INITIALIZES START AND END RATES.
  1524                              <1> ;-------------------------------------------------------------------------------
  1525                              <1> SETUP_STATE:
  1526 00004155 F687[155F0100]10    <1> 	TEST	byte [DSK_STATE+eDI], MED_DET ; MEDIA DETERMINED ?
  1527 0000415C 7537                <1> 	JNZ	short J1C		; NO STATES IF DETERMINED
  1528 0000415E 66B84000            <1>         MOV     AX,(RATE_500*256)+RATE_300  ; AH = START RATE, AL = END RATE
  1529 00004162 F687[155F0100]04    <1> 	TEST	byte [DSK_STATE+eDI],DRV_DET ; DRIVE ?
  1530 00004169 740D                <1> 	JZ	short AX_SET		; DO NOT KNOW DRIVE
  1531 0000416B F687[155F0100]02    <1> 	TEST	byte [DSK_STATE+eDI], FMT_CAPA ; MULTI-RATE?
  1532 00004172 7504                <1> 	JNZ	short AX_SET		; JUMP IF YES
  1533 00004174 66B88080            <1>         MOV     AX,RATE_250*257         ; START A END RATE 250 FOR 360 DRIVE
  1534                              <1> AX_SET:	
  1535 00004178 80A7[155F0100]1F    <1> 	AND	byte [DSK_STATE+eDI], ~(RATE_MSK+DBL_STEP) ; TURN OFF THE RATE
  1536 0000417F 08A7[155F0100]      <1> 	OR	[DSK_STATE+eDI], AH	; RATE FIRST TO TRY
  1537 00004185 8025[105F0100]F3    <1> 	AND	byte [LASTRATE], ~STRT_MSK ; ERASE LAST TO TRY RATE BITS
  1538 0000418C C0C804              <1> 	ROR	AL,4			; TO OPERATION LAST RATE LOCATION
  1539 0000418F 0805[105F0100]      <1> 	OR	[LASTRATE], AL		; LAST RATE
  1540                              <1> J1C:	
  1541 00004195 C3                  <1> 	RETn
  1542                              <1> 
  1543                              <1> ;-------------------------------------------------------------------------------
  1544                              <1> ;  FMT_INIT: ESTABLISH STATE IF UNESTABLISHED AT FORMAT TIME.
  1545                              <1> ;-------------------------------------------------------------------------------
  1546                              <1> FMT_INIT:
  1547 00004196 F687[155F0100]10    <1> 	TEST	byte [DSK_STATE+eDI], MED_DET ; IS MEDIA ESTABLISHED
  1548 0000419D 7546                <1> 	JNZ	short F1_OUT		; IF SO RETURN
  1549 0000419F E82C040000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN AL
  1550                              <1> 	;; 20/02/2015
  1551                              <1> 	;;JC	short CL_DRV		; ERROR IN CMOS ASSUME NO DRIVE
  1552 000041A4 7440                <1> 	jz	short CL_DRV ;; 20/02/2015
  1553 000041A6 FEC8                <1> 	DEC	AL			; MAKE ZERO ORIGIN
  1554                              <1> 	;;JS	short CL_DRV		; NO DRIVE IF AL 0
  1555 000041A8 8AA7[155F0100]      <1> 	MOV	AH, [DSK_STATE+eDI]	; AH = CURRENT STATE
  1556 000041AE 80E40F              <1> 	AND	AH, ~(MED_DET+DBL_STEP+RATE_MSK) ; CLEAR
  1557 000041B1 08C0                <1> 	OR	AL,AL			; CHECK FOR 360
  1558 000041B3 7505                <1> 	JNZ	short N_360		; IF 360 WILL BE 0
  1559 000041B5 80CC90              <1> 	OR	AH,MED_DET+RATE_250	; ESTABLISH MEDIA
  1560 000041B8 EB25                <1> 	JMP	SHORT SKP_STATE		; SKIP OTHER STATE PROCESSING
  1561                              <1> N_360:	
  1562 000041BA FEC8                <1> 	DEC	AL			; 1.2 M DRIVE
  1563 000041BC 7505                <1> 	JNZ	short N_12		; JUMP IF NOT
  1564                              <1> F1_RATE:
  1565 000041BE 80CC10              <1> 	OR	AH,MED_DET+RATE_500	; SET FORMAT RATE
  1566 000041C1 EB1C                <1> 	JMP	SHORT SKP_STATE		; SKIP OTHER STATE PROCESSING
  1567                              <1> N_12:	
  1568 000041C3 FEC8                <1> 	DEC	AL			; CHECK FOR TYPE 3
  1569 000041C5 750F                <1> 	JNZ	short N_720		; JUMP IF NOT
  1570 000041C7 F6C404              <1> 	TEST	AH,DRV_DET		; IS DRIVE DETERMINED
  1571 000041CA 7410                <1> 	JZ	short ISNT_12		; TREAT AS NON 1.2 DRIVE
  1572 000041CC F6C402              <1> 	TEST	AH,FMT_CAPA		; IS 1.2M
  1573 000041CF 740B                <1> 	JZ	short ISNT_12		; JUMP IF NOT
  1574 000041D1 80CC50              <1> 	OR	AH,MED_DET+RATE_300	; RATE 300
  1575 000041D4 EB09                <1> 	JMP	SHORT SKP_STATE		; CONTINUE
  1576                              <1> N_720:
  1577 000041D6 FEC8                <1> 	DEC	AL			; CHECK FOR TYPE 4
  1578 000041D8 750C                <1> 	JNZ	short CL_DRV		; NO DRIVE, CMOS BAD
  1579 000041DA EBE2                <1> 	JMP	SHORT F1_RATE
  1580                              <1> ISNT_12: 
  1581 000041DC 80CC90              <1> 	OR	AH,MED_DET+RATE_250	; MUST BE RATE 250
  1582                              <1> 
  1583                              <1> SKP_STATE:
  1584 000041DF 88A7[155F0100]      <1> 	MOV	[DSK_STATE+eDI], AH	; STORE AWAY
  1585                              <1> F1_OUT:
  1586 000041E5 C3                  <1> 	RETn
  1587                              <1> CL_DRV:	
  1588 000041E6 30E4                <1> 	XOR	AH,AH			; CLEAR STATE
  1589 000041E8 EBF5                <1> 	JMP	SHORT SKP_STATE		; SAVE IT
  1590                              <1> 
  1591                              <1> ;-------------------------------------------------------------------------------
  1592                              <1> ; MED_CHANGE	
  1593                              <1> ;	CHECKS FOR MEDIA CHANGE, RESETS MEDIA CHANGE, 
  1594                              <1> ;	CHECKS MEDIA CHANGE AGAIN.
  1595                              <1> ;
  1596                              <1> ; ON EXIT:	CY = 1 MEANS MEDIA CHANGE OR TIMEOUT
  1597                              <1> ;		@DSKETTE_STATUS = ERROR CODE
  1598                              <1> ;-------------------------------------------------------------------------------
  1599                              <1> MED_CHANGE:
  1600 000041EA E888060000          <1> 	CALL	READ_DSKCHNG		; READ DISK CHANCE LINE STATE
  1601 000041EF 7447                <1> 	JZ	short MC_OUT		; BYPASS HANDLING DISK CHANGE LINE
  1602 000041F1 80A7[155F0100]EF    <1> 	AND	byte [DSK_STATE+eDI], ~MED_DET ; CLEAR STATE FOR THIS DRIVE
  1603                              <1> 
  1604                              <1> ;	THIS SEQUENCE ENSURES WHENEVER A DISKETTE IS CHANGED THAT
  1605                              <1> ;	ON THE NEXT OPERATION THE REQUIRED MOTOR START UP TIME WILL
  1606                              <1> ;	BE WAITED. (DRIVE MOTOR MAY GO OFF UPON DOOR OPENING).
  1607                              <1> 
  1608 000041F8 6689F9              <1> 	MOV	CX,DI			; CL = DRIVE 0
  1609 000041FB B001                <1> 	MOV	AL,1			; MOTOR ON BIT MASK
  1610 000041FD D2E0                <1> 	SHL	AL,CL			; TO APPROPRIATE POSITION
  1611 000041FF F6D0                <1> 	NOT	AL			; KEEP ALL BUT MOTOR ON
  1612 00004201 FA                  <1> 	CLI				; NO INTERRUPTS
  1613 00004202 2005[065F0100]      <1> 	AND	[MOTOR_STATUS], AL	; TURN MOTOR OFF INDICATOR
  1614 00004208 FB                  <1> 	STI				; INTERRUPTS ENABLED
  1615 00004209 E810040000          <1> 	CALL	MOTOR_ON		; TURN MOTOR ON
  1616                              <1> 
  1617                              <1> ;-----	THIS SEQUENCE OF SEEKS IS USED TO RESET DISKETTE CHANGE SIGNAL
  1618                              <1> 
  1619 0000420E E850F9FFFF          <1> 	CALL	DSK_RESET		; RESET NEC
  1620 00004213 B501                <1> 	MOV	CH,01H			; MOVE TO CYLINDER 1
  1621 00004215 E8FF040000          <1> 	CALL	SEEK			; ISSUE SEEK
  1622 0000421A 30ED                <1> 	XOR	CH,CH			; MOVE TO CYLINDER 0
  1623 0000421C E8F8040000          <1> 	CALL	SEEK			; ISSUE SEEK
  1624 00004221 C605[085F0100]06    <1> 	MOV	byte [DSKETTE_STATUS], MEDIA_CHANGE ; STORE IN STATUS
  1625                              <1> OK1:
  1626 00004228 E84A060000          <1> 	CALL	READ_DSKCHNG		; CHECK MEDIA CHANGED AGAIN
  1627 0000422D 7407                <1> 	JZ	short OK2		; IF ACTIVE, NO DISKETTE, TIMEOUT
  1628                              <1> OK4:
  1629 0000422F C605[085F0100]80    <1> 	MOV	byte [DSKETTE_STATUS], TIME_OUT ; TIMEOUT IF DRIVE EMPTY
  1630                              <1> OK2:		
  1631 00004236 F9                  <1> 	STC				; MEDIA CHANGED, SET CY
  1632 00004237 C3                  <1> 	RETn
  1633                              <1> MC_OUT:
  1634 00004238 F8                  <1> 	CLC				; NO MEDIA CHANGED, CLEAR CY
  1635 00004239 C3                  <1> 	RETn
  1636                              <1> 
  1637                              <1> ;-------------------------------------------------------------------------------
  1638                              <1> ; SEND_RATE
  1639                              <1> ;	SENDS DATA RATE COMMAND TO NEC
  1640                              <1> ; ON ENTRY:	DI = DRIVE #
  1641                              <1> ; ON EXIT:	NONE
  1642                              <1> ; REGISTERS ALTERED: DX
  1643                              <1> ;-------------------------------------------------------------------------------
  1644                              <1> SEND_RATE:
  1645 0000423A 6650                <1> 	PUSH	AX			; SAVE REG.
  1646 0000423C 8025[105F0100]3F    <1> 	AND	byte [LASTRATE], ~SEND_MSK ; ELSE CLEAR LAST RATE ATTEMPTED
  1647 00004243 8A87[155F0100]      <1> 	MOV	AL, [DSK_STATE+eDI]	; GET RATE STATE OF THIS DRIVE
  1648 00004249 24C0                <1> 	AND	AL,SEND_MSK		; KEEP ONLY RATE BITS
  1649 0000424B 0805[105F0100]      <1> 	OR	[LASTRATE], AL		; SAVE NEW RATE FOR NEXT CHECK
  1650 00004251 C0C002              <1> 	ROL	AL,2			; MOVE TO BIT OUTPUT POSITIONS
  1651 00004254 66BAF703            <1> 	MOV	DX,03F7H		; OUTPUT NEW DATA RATE
  1652 00004258 EE                  <1> 	OUT	DX,AL
  1653 00004259 6658                <1> 	POP	AX			; RESTORE REG.
  1654 0000425B C3                  <1> 	RETn
  1655                              <1> 
  1656                              <1> ;-------------------------------------------------------------------------------
  1657                              <1> ; CHK_LASTRATE
  1658                              <1> ;	CHECK PREVIOUS DATE RATE SNT TO THE CONTROLLER.
  1659                              <1> ; ON ENTRY:
  1660                              <1> ;	DI = DRIVE #
  1661                              <1> ; ON EXIT:
  1662                              <1> ;	ZF =  1 DATA RATE IS THE SAME AS THE LAST RATE SENT TO NEC
  1663                              <1> ;	ZF =  0 DATA RATE IS DIFFERENT FROM LAST RATE
  1664                              <1> ; REGISTERS ALTERED: DX
  1665                              <1> ;-------------------------------------------------------------------------------
  1666                              <1> CHK_LASTRATE:
  1667 0000425C 6650                <1> 	PUSH	AX			; SAVE REG
  1668 0000425E 2225[105F0100]      <1> 	AND	AH, [LASTRATE]		; GET LAST DATA RATE SELECTED
  1669 00004264 8A87[155F0100]      <1> 	MOV	AL, [DSK_STATE+eDI]	; GET RATE STATE OF THIS DRIVE
  1670 0000426A 6625C0C0            <1>         AND     AX, SEND_MSK*257        ; KEEP ONLY RATE BITS OF BOTH
  1671 0000426E 38E0                <1> 	CMP	AL, AH			; COMPARE TO PREVIOUSLY TRIED
  1672                              <1> 					; ZF = 1 RATE IS THE SAME
  1673 00004270 6658                <1> 	POP	AX			; RESTORE REG.
  1674 00004272 C3                  <1> 	RETn
  1675                              <1> 
  1676                              <1> ;-------------------------------------------------------------------------------
  1677                              <1> ; DMA_SETUP
  1678                              <1> ;	THIS ROUTINE SETS UP THE DMA FOR READ/WRITE/VERIFY OPERATIONS.
  1679                              <1> ;
  1680                              <1> ; ON ENTRY:	AL = DMA COMMAND
  1681                              <1> ;
  1682                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  1683                              <1> ;-------------------------------------------------------------------------------
  1684                              <1> 
  1685                              <1> ; SI = Head #, # of Sectors or DASD Type
  1686                              <1> 
  1687                              <1> ; 22/08/2015
  1688                              <1> ; 08/02/2015 - Protected Mode Modification
  1689                              <1> ; 06/02/2015 - 07/02/2015
  1690                              <1> ; NOTE: Buffer address must be in 1st 16MB of Physical Memory (24 bit limit).
  1691                              <1> ; (DMA Addres = Physical Address)
  1692                              <1> ; (Retro UNIX 386 v1 Kernel/System Mode Virtual Address = Physical Address)
  1693                              <1> ;
  1694                              <1> 
  1695                              <1> 
  1696                              <1> ; 04/02/2016 (clc)
  1697                              <1> ; 20/02/2015 modification (source: AWARD BIOS 1999, DMA_SETUP)
  1698                              <1> ; 16/12/2014 (IODELAY)
  1699                              <1> 
  1700                              <1> DMA_SETUP:
  1701                              <1> 
  1702                              <1> ;; 20/02/2015
  1703 00004273 8B5504              <1> 	mov	edx, [ebp+4] 		; Buffer address
  1704 00004276 F7C2000000FF        <1> 	test	edx, 0FF000000h		; 16 MB limit (22/08/2015, bugfix)
  1705 0000427C 756E                <1> 	jnz	short dma_bnd_err_stc
  1706                              <1> 	;
  1707 0000427E 6650                <1> 	push	ax			; DMA command
  1708 00004280 52                  <1> 	push	edx			; *
  1709 00004281 B203                <1> 	mov	dl, 3			; GET BYTES/SECTOR PARAMETER
  1710 00004283 E851030000          <1> 	call	GET_PARM		; 
  1711 00004288 88E1                <1> 	mov	cl, ah 			; SHIFT COUNT (0=128, 1=256, 2=512 ETC)
  1712 0000428A 6689F0              <1> 	mov	ax, si			; Sector count
  1713 0000428D 88C4                <1> 	mov	ah, al			; AH =  # OF SECTORS
  1714 0000428F 28C0                <1> 	sub	al, al			; AL = 0, AX = # SECTORS * 256
  1715 00004291 66D1E8              <1> 	shr	ax, 1			; AX = # SECTORS * 128
  1716 00004294 66D3E0              <1> 	shl	ax, cl			; SHIFT BY PARAMETER VALUE
  1717 00004297 6648                <1> 	dec	ax			; -1 FOR DMA VALUE
  1718 00004299 6689C1              <1> 	mov	cx, ax
  1719 0000429C 5A                  <1> 	pop	edx			; *
  1720 0000429D 6658                <1> 	pop	ax
  1721 0000429F 3C42                <1> 	cmp	al, 42h
  1722 000042A1 7507                <1>         jne     short NOT_VERF
  1723 000042A3 BA0000FF00          <1> 	mov	edx, 0FF0000h
  1724 000042A8 EB08                <1> 	jmp	short J33
  1725                              <1> NOT_VERF:
  1726 000042AA 6601CA              <1> 	add	dx, cx			; check for overflow
  1727 000042AD 723E                <1> 	jc	short dma_bnd_err
  1728                              <1> 	;
  1729 000042AF 6629CA              <1> 	sub	dx, cx			; Restore start address
  1730                              <1> J33:
  1731 000042B2 FA                  <1> 	CLI				; DISABLE INTERRUPTS DURING DMA SET-UP
  1732 000042B3 E60C                <1> 	OUT	DMA+12,AL		; SET THE FIRST/LA5T F/F
  1733                              <1> 	IODELAY				; WAIT FOR I/O
  1733 000042B5 EB00                <2>  jmp short $+2
  1733 000042B7 EB00                <2>  jmp short $+2
  1734 000042B9 E60B                <1> 	OUT	DMA+11,AL		; OUTPUT THE MODE BYTE
  1735 000042BB 89D0                <1> 	mov	eax, edx		; Buffer address
  1736 000042BD E604                <1> 	OUT	DMA+4,AL		; OUTPUT LOW ADDRESS
  1737                              <1> 	IODELAY				; WAIT FOR I/O
  1737 000042BF EB00                <2>  jmp short $+2
  1737 000042C1 EB00                <2>  jmp short $+2
  1738 000042C3 88E0                <1> 	MOV	AL,AH
  1739 000042C5 E604                <1> 	OUT	DMA+4,AL		; OUTPUT HIGH ADDRESS
  1740 000042C7 C1E810              <1> 	shr	eax, 16
  1741                              <1> 	IODELAY				; I/O WAIT STATE
  1741 000042CA EB00                <2>  jmp short $+2
  1741 000042CC EB00                <2>  jmp short $+2
  1742 000042CE E681                <1> 	OUT	081H,AL			; OUTPUT highest BITS TO PAGE REGISTER
  1743                              <1> 	IODELAY
  1743 000042D0 EB00                <2>  jmp short $+2
  1743 000042D2 EB00                <2>  jmp short $+2
  1744 000042D4 6689C8              <1> 	mov	ax, cx			; Byte count - 1
  1745 000042D7 E605                <1> 	OUT	DMA+5,AL		; LOW BYTE OF COUNT
  1746                              <1> 	IODELAY				; WAIT FOR I/O
  1746 000042D9 EB00                <2>  jmp short $+2
  1746 000042DB EB00                <2>  jmp short $+2
  1747 000042DD 88E0                <1> 	MOV	AL, AH
  1748 000042DF E605                <1> 	OUT	DMA+5,AL		; HIGH BYTE OF COUNT
  1749                              <1> 	IODELAY
  1749 000042E1 EB00                <2>  jmp short $+2
  1749 000042E3 EB00                <2>  jmp short $+2
  1750 000042E5 FB                  <1> 	STI				; RE-ENABLE INTERRUPTS
  1751 000042E6 B002                <1> 	MOV	AL, 2			; MODE FOR 8237
  1752 000042E8 E60A                <1> 	OUT	DMA+10, AL		; INITIALIZE THE DISKETTE CHANNEL
  1753                              <1> 
  1754 000042EA F8                  <1> 	clc	; 04/02/2016
  1755 000042EB C3                  <1> 	retn
  1756                              <1> 
  1757                              <1> dma_bnd_err_stc:
  1758 000042EC F9                  <1> 	stc
  1759                              <1> dma_bnd_err:
  1760 000042ED C605[085F0100]09    <1> 	MOV	byte [DSKETTE_STATUS], DMA_BOUNDARY ; SET ERROR
  1761 000042F4 C3                  <1> 	RETn				; CY SET BY ABOVE IF ERROR
  1762                              <1> 
  1763                              <1> ;; 16/12/2014
  1764                              <1> ;;	CLI				; DISABLE INTERRUPTS DURING DMA SET-UP
  1765                              <1> ;;	OUT	DMA+12,AL		; SET THE FIRST/LA5T F/F
  1766                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1767                              <1> ;;	IODELAY
  1768                              <1> ;; 	OUT	DMA+11,AL		; OUTPUT THE MODE BYTE
  1769                              <1> ;;	;SIODELAY
  1770                              <1> ;;      ;CMP	AL, 42H			; DMA VERIFY COMMAND
  1771                              <1> ;;      ;JNE	short NOT_VERF		; NO
  1772                              <1> ;;      ;XOR	AX, AX			; START ADDRESS
  1773                              <1> ;;      ;JMP	SHORT J33
  1774                              <1> ;;;NOT_VERF:	
  1775                              <1> ;;	;MOV	AX,ES			; GET THE ES VALUE
  1776                              <1> ;;	;ROL	AX,4			; ROTATE LEFT
  1777                              <1> ;;	;MOV	CH,AL			; GET HIGHEST NIBBLE OF ES TO CH
  1778                              <1> ;;	;AND	AL,11110000B		; ZERO THE LOW NIBBLE FROM SEGMENT
  1779                              <1> ;;	;ADD	AX,[BP+2]		; TEST FOR CARRY FROM ADDITION
  1780                              <1> ;;	mov	eax, [ebp+4] ; 06/02/2015	
  1781                              <1> ;;	;JNC	short J33
  1782                              <1> ;;	;INC	CH			; CARRY MEANS HIGH 4 BITS MUST BE INC
  1783                              <1> ;;;J33:
  1784                              <1> ;;	PUSH	eAX			; SAVE START ADDRESS
  1785                              <1> ;;	OUT	DMA+4,AL		; OUTPUT LOW ADDRESS
  1786                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1787                              <1> ;;	IODELAY
  1788                              <1> ;;	MOV	AL,AH
  1789                              <1> ;;	OUT	DMA+4,AL		; OUTPUT HIGH ADDRESS
  1790                              <1> ;;	shr	eax, 16	     ; 07/02/2015
  1791                              <1> ;;	;MOV	AL,CH			; GET HIGH 4 BITS
  1792                              <1> ;;	;JMP	$+2			; I/O WAIT STATE
  1793                              <1> ;;	IODELAY
  1794                              <1> ;;	;AND	AL,00001111B
  1795                              <1> ;;	OUT	081H,AL			; OUTPUT HIGH 4 BITS TO PAGE REGISTER
  1796                              <1> ;;	;SIODELAY
  1797                              <1> ;;
  1798                              <1> ;;;----- DETERMINE COUNT
  1799                              <1> ;;	sub	eax, eax ; 08/02/2015
  1800                              <1> ;;	MOV	AX, SI			; AL =  # OF SECTORS
  1801                              <1> ;;	XCHG	AL, AH			; AH =  # OF SECTORS
  1802                              <1> ;;	SUB	AL, AL			; AL = 0, AX = # SECTORS * 256
  1803                              <1> ;;	SHR	AX, 1			; AX = # SECTORS * 128
  1804                              <1> ;;	PUSH	AX			; SAVE # OF SECTORS * 128
  1805                              <1> ;;	MOV	DL, 3			; GET BYTES/SECTOR PARAMETER
  1806                              <1> ;;	CALL	GET_PARM		; "
  1807                              <1> ;;	MOV	CL,AH			; SHIFT COUNT (0=128, 1=256, 2=512 ETC)
  1808                              <1> ;;	POP	AX			; AX = # SECTORS * 128
  1809                              <1> ;;	SHL	AX,CL			; SHIFT BY PARAMETER VALUE
  1810                              <1> ;;	DEC	AX			; -1 FOR DMA VALUE
  1811                              <1> ;;	PUSH	eAX  ; 08/02/2015	; SAVE COUNT VALUE
  1812                              <1> ;;	OUT	DMA+5,AL		; LOW BYTE OF COUNT
  1813                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1814                              <1> ;;	IODELAY
  1815                              <1> ;;	MOV	AL, AH
  1816                              <1> ;;	OUT	DMA+5,AL		; HIGH BYTE OF COUNT
  1817                              <1> ;;	;IODELAY
  1818                              <1> ;;	STI				; RE-ENABLE INTERRUPTS
  1819                              <1> ;;	POP	eCX  ; 08/02/2015 	; RECOVER COUNT VALUE
  1820                              <1> ;;	POP	eAX  ; 08/02/2015	; RECOVER ADDRESS VALUE
  1821                              <1> ;;	;ADD	AX, CX			; ADD, TEST FOR 64K OVERFLOW
  1822                              <1> ;;	add	ecx, eax ; 08/02/2015
  1823                              <1> ;;	MOV	AL, 2			; MODE FOR 8237
  1824                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1825                              <1> ;;	SIODELAY
  1826                              <1> ;;	OUT	DMA+10, AL		; INITIALIZE THE DISKETTE CHANNEL
  1827                              <1> ;;	;JNC	short NO_BAD		; CHECK FOR ERROR
  1828                              <1> ;;	jc	short dma_bnd_err ; 08/02/2015
  1829                              <1> ;;	and	ecx, 0FFF00000h ; 16 MB limit
  1830                              <1> ;;	jz	short NO_BAD
  1831                              <1> ;;dma_bnd_err:
  1832                              <1> ;;	MOV	byte [DSKETTE_STATUS], DMA_BOUNDARY ; SET ERROR
  1833                              <1> ;;NO_BAD:
  1834                              <1> ;;	RETn				; CY SET BY ABOVE IF ERROR
  1835                              <1> 
  1836                              <1> ;-------------------------------------------------------------------------------
  1837                              <1> ; FMTDMA_SET
  1838                              <1> ;	THIS ROUTINE SETS UP THE DMA CONTROLLER FOR A FORMAT OPERATION.
  1839                              <1> ;
  1840                              <1> ; ON ENTRY:	NOTHING REQUIRED
  1841                              <1> ;
  1842                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  1843                              <1> ;-------------------------------------------------------------------------------
  1844                              <1> 
  1845                              <1> FMTDMA_SET:
  1846                              <1> ;; 20/02/2015 modification	
  1847 000042F5 8B5504              <1> 	mov	edx, [ebp+4] 		; Buffer address
  1848 000042F8 F7C20000F0FF        <1> 	test	edx, 0FFF00000h		; 16 MB limit
  1849 000042FE 75EC                <1> 	jnz	short dma_bnd_err_stc
  1850                              <1> 	;
  1851 00004300 6652                <1> 	push	dx			; *
  1852 00004302 B204                <1> 	mov	DL, 4			; SECTORS/TRACK VALUE IN PARM TABLE
  1853 00004304 E8D0020000          <1> 	call	GET_PARM		; "
  1854 00004309 88E0                <1> 	mov	al, ah			; AL = SECTORS/TRACK VALUE
  1855 0000430B 28E4                <1> 	sub	ah, ah			; AX = SECTORS/TRACK VALUE
  1856 0000430D 66C1E002            <1> 	shl	ax, 2			; AX = SEC/TRK * 4 (OFFSET C,H,R,N)
  1857 00004311 6648                <1> 	dec	ax			; -1 FOR DMA VALUE
  1858 00004313 6689C1              <1> 	mov	cx, ax
  1859 00004316 665A                <1> 	pop	dx			; *
  1860 00004318 6601CA              <1> 	add	dx, cx			; check for overflow
  1861 0000431B 72D0                <1> 	jc	short dma_bnd_err
  1862                              <1> 	;
  1863 0000431D 6629CA              <1> 	sub	dx, cx			; Restore start address
  1864                              <1> 	;
  1865 00004320 B04A                <1> 	MOV	AL, 04AH		; WILL WRITE TO THE DISKETTE
  1866 00004322 FA                  <1> 	CLI				; DISABLE INTERRUPTS DURING DMA SET-UP
  1867 00004323 E60C                <1> 	OUT	DMA+12,AL		; SET THE FIRST/LA5T F/F
  1868                              <1> 	IODELAY				; WAIT FOR I/O
  1868 00004325 EB00                <2>  jmp short $+2
  1868 00004327 EB00                <2>  jmp short $+2
  1869 00004329 E60B                <1> 	OUT	DMA+11,AL		; OUTPUT THE MODE BYTE
  1870 0000432B 89D0                <1> 	mov	eax, edx		; Buffer address
  1871 0000432D E604                <1> 	OUT	DMA+4,AL		; OUTPUT LOW ADDRESS
  1872                              <1> 	IODELAY				; WAIT FOR I/O
  1872 0000432F EB00                <2>  jmp short $+2
  1872 00004331 EB00                <2>  jmp short $+2
  1873 00004333 88E0                <1> 	MOV	AL,AH
  1874 00004335 E604                <1> 	OUT	DMA+4,AL		; OUTPUT HIGH ADDRESS
  1875 00004337 C1E810              <1> 	shr	eax, 16
  1876                              <1> 	IODELAY				; I/O WAIT STATE
  1876 0000433A EB00                <2>  jmp short $+2
  1876 0000433C EB00                <2>  jmp short $+2
  1877 0000433E E681                <1> 	OUT	081H,AL			; OUTPUT highest BITS TO PAGE REGISTER
  1878                              <1> 	IODELAY
  1878 00004340 EB00                <2>  jmp short $+2
  1878 00004342 EB00                <2>  jmp short $+2
  1879 00004344 6689C8              <1> 	mov	ax, cx			; Byte count - 1
  1880 00004347 E605                <1> 	OUT	DMA+5,AL		; LOW BYTE OF COUNT
  1881                              <1> 	IODELAY				; WAIT FOR I/O
  1881 00004349 EB00                <2>  jmp short $+2
  1881 0000434B EB00                <2>  jmp short $+2
  1882 0000434D 88E0                <1> 	MOV	AL, AH
  1883 0000434F E605                <1> 	OUT	DMA+5,AL		; HIGH BYTE OF COUNT
  1884                              <1> 	IODELAY
  1884 00004351 EB00                <2>  jmp short $+2
  1884 00004353 EB00                <2>  jmp short $+2
  1885 00004355 FB                  <1> 	STI				; RE-ENABLE INTERRUPTS
  1886 00004356 B002                <1> 	MOV	AL, 2			; MODE FOR 8237
  1887 00004358 E60A                <1> 	OUT	DMA+10, AL		; INITIALIZE THE DISKETTE CHANNEL
  1888 0000435A C3                  <1> 	retn
  1889                              <1> 
  1890                              <1> ;; 08/02/2015 - Protected Mode Modification
  1891                              <1> ;;	MOV	AL, 04AH		; WILL WRITE TO THE DISKETTE
  1892                              <1> ;;	CLI				; DISABLE INTERRUPTS DURING DMA SET-UP
  1893                              <1> ;;	OUT	DMA+12,AL		; SET THE FIRST/LA5T F/F
  1894                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1895                              <1> ;;	IODELAY
  1896                              <1> ;;	OUT	DMA+11,AL		; OUTPUT THE MODE BYTE
  1897                              <1> ;;	;MOV	AX,ES			; GET THE ES VALUE
  1898                              <1> ;;	;ROL	AX,4			; ROTATE LEFT
  1899                              <1> ;;	;MOV	CH,AL			; GET HIGHEST NIBBLE OF ES TO CH
  1900                              <1> ;;	;AND	AL,11110000B		; ZERO THE LOW NIBBLE FROM SEGMENT
  1901                              <1> ;;	;ADD	AX,[BP+2]		; TEST FOR CARRY FROM ADDITION
  1902                              <1> ;;	;JNC	short J33A
  1903                              <1> ;;	;INC	CH			; CARRY MEANS HIGH 4 BITS MUST BE INC
  1904                              <1> ;;	mov	eax, [ebp+4] ; 08/02/2015
  1905                              <1> ;;;J33A:
  1906                              <1> ;;	PUSH	eAX ; 08/02/2015	; SAVE START ADDRESS
  1907                              <1> ;;	OUT	DMA+4,AL		; OUTPUT LOW ADDRESS
  1908                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1909                              <1> ;;	IODELAY
  1910                              <1> ;;	MOV	AL,AH
  1911                              <1> ;;	OUT	DMA+4,AL		; OUTPUT HIGH ADDRESS
  1912                              <1> ;;	shr 	eax, 16 ; 08/02/2015
  1913                              <1> ;;	;MOV	AL,CH			; GET HIGH 4 BITS
  1914                              <1> ;;	;JMP	$+2			; I/O WAIT STATE
  1915                              <1> ;;	IODELAY
  1916                              <1> ;;	;AND	AL,00001111B
  1917                              <1> ;;	OUT	081H,AL			; OUTPUT HIGH 4 BITS TO PAGE REGISTER
  1918                              <1> ;;
  1919                              <1> ;;;----- DETERMINE COUNT
  1920                              <1> ;;	sub	eax, eax ; 08/02/2015
  1921                              <1> ;;	MOV	DL, 4			; SECTORS/TRACK VALUE IN PARM TABLE
  1922                              <1> ;;	CALL	GET_PARM		; "
  1923                              <1> ;;	XCHG	AL, AH			; AL = SECTORS/TRACK VALUE
  1924                              <1> ;;	SUB	AH, AH			; AX = SECTORS/TRACK VALUE
  1925                              <1> ;;	SHL	AX, 2			; AX = SEC/TRK * 4 (OFFSET C,H,R,N)
  1926                              <1> ;;	DEC	AX			; -1 FOR DMA VALUE
  1927                              <1> ;;	PUSH	eAX 	; 08/02/2015	; SAVE # OF BYTES TO BE TRANSFERED
  1928                              <1> ;;	OUT	DMA+5,AL		; LOW BYTE OF COUNT
  1929                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1930                              <1> ;;	IODELAY
  1931                              <1> ;;	MOV	AL, AH
  1932                              <1> ;;	OUT	DMA+5,AL		; HIGH BYTE OF COUNT
  1933                              <1> ;;	STI				; RE-ENABLE INTERRUPTS
  1934                              <1> ;;	POP	eCX	; 08/02/2015	; RECOVER COUNT VALUE
  1935                              <1> ;;	POP	eAX	; 08/02/2015	; RECOVER ADDRESS VALUE
  1936                              <1> ;;	;ADD	AX, CX			; ADD, TEST FOR 64K OVERFLOW
  1937                              <1> ;;	add	ecx, eax ; 08/02/2015
  1938                              <1> ;;	MOV	AL, 2			; MODE FOR 8237
  1939                              <1> ;;	;JMP	$+2			; WAIT FOR I/O
  1940                              <1> ;;	SIODELAY
  1941                              <1> ;;	OUT	DMA+10, AL		; INITIALIZE THE DISKETTE CHANNEL
  1942                              <1> ;;	;JNC	short FMTDMA_OK		; CHECK FOR ERROR
  1943                              <1> ;;	jc	short fmtdma_bnd_err ; 08/02/2015
  1944                              <1> ;;	and	ecx, 0FFF00000h  ; 16 MB limit
  1945                              <1> ;;	jz	short FMTDMA_OK
  1946                              <1> ;;	stc	; 20/02/2015
  1947                              <1> ;;fmtdma_bnd_err:
  1948                              <1> ;;	MOV	byte [DSKETTE_STATUS], DMA_BOUNDARY ; SET ERROR
  1949                              <1> ;;FMTDMA_OK:
  1950                              <1> ;;	RETn				; CY SET BY ABOVE IF ERROR
  1951                              <1> 
  1952                              <1> ;-------------------------------------------------------------------------------
  1953                              <1> ; NEC_INIT	
  1954                              <1> ;	THIS ROUTINE SEEKS TO THE REQUESTED TRACK AND INITIALIZES
  1955                              <1> ;	THE NEC FOR THE READ/WRITE/VERIFY/FORMAT OPERATION.
  1956                              <1> ;
  1957                              <1> ; ON ENTRY:	AH = NEC COMMAND TO BE PERFORMED
  1958                              <1> ;
  1959                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  1960                              <1> ;-------------------------------------------------------------------------------
  1961                              <1> NEC_INIT:
  1962 0000435B 6650                <1> 	PUSH	AX			; SAVE NEC COMMAND
  1963 0000435D E8BC020000          <1> 	CALL	MOTOR_ON		; TURN MOTOR ON FOR SPECIFIC DRIVE
  1964                              <1> 
  1965                              <1> ;-----	DO THE SEEK OPERATION
  1966                              <1> 
  1967 00004362 8A6D01              <1> 	MOV	CH,[eBP+1]		; CH = TRACK #
  1968 00004365 E8AF030000          <1> 	CALL	SEEK			; MOVE TO CORRECT TRACK
  1969 0000436A 6658                <1> 	POP	AX			; RECOVER COMMAND
  1970 0000436C 721E                <1> 	JC	short ER_1		; ERROR ON SEEK
  1971 0000436E BB[8C430000]        <1> 	MOV	eBX, ER_1		; LOAD ERROR ADDRESS
  1972 00004373 53                  <1> 	PUSH	eBX			; PUSH NEC_OUT ERROR RETURN
  1973                              <1> 
  1974                              <1> ;-----	SEND OUT THE PARAMETERS TO THE CONTROLLER
  1975                              <1> 
  1976 00004374 E866030000          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE OPERATION COMMAND
  1977 00004379 6689F0              <1> 	MOV	AX,SI			; AH = HEAD #
  1978 0000437C 89FB                <1> 	MOV	eBX,eDI			; BL = DRIVE #
  1979 0000437E C0E402              <1> 	SAL	AH,2			; MOVE IT TO BIT 2
  1980 00004381 80E404              <1> 	AND	AH,00000100B		; ISOLATE THAT BIT
  1981 00004384 08DC                <1> 	OR	AH,BL			; OR IN THE DRIVE NUMBER
  1982 00004386 E854030000          <1> 	CALL	NEC_OUTPUT		; FALL THRU CY SET IF ERROR
  1983 0000438B 5B                  <1> 	POP	eBX			; THROW AWAY ERROR RETURN
  1984                              <1> ER_1:
  1985 0000438C C3                  <1> 	RETn
  1986                              <1> 
  1987                              <1> ;-------------------------------------------------------------------------------
  1988                              <1> ; RWV_COM
  1989                              <1> ;	THIS ROUTINE SENDS PARAMETERS TO THE NEC SPECIFIC TO THE 
  1990                              <1> ;	READ/WRITE/VERIFY OPERATIONS.
  1991                              <1> ;
  1992                              <1> ; ON ENTRY:	CS:BX = ADDRESS OF MEDIA/DRIVE PARAMETER TABLE
  1993                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  1994                              <1> ;-------------------------------------------------------------------------------
  1995                              <1> RWV_COM:
  1996 0000438D B8[D8430000]        <1> 	MOV	eAX, ER_2		; LOAD ERROR ADDRESS
  1997 00004392 50                  <1> 	PUSH	eAX			; PUSH NEC_OUT ERROR RETURN
  1998 00004393 8A6501              <1> 	MOV	AH,[eBP+1]		; OUTPUT TRACK #
  1999 00004396 E844030000          <1> 	CALL	NEC_OUTPUT
  2000 0000439B 6689F0              <1> 	MOV	AX,SI			; OUTPUT HEAD #
  2001 0000439E E83C030000          <1> 	CALL	NEC_OUTPUT
  2002 000043A3 8A6500              <1>         MOV     AH,[eBP]                ; OUTPUT SECTOR #
  2003 000043A6 E834030000          <1> 	CALL	NEC_OUTPUT
  2004 000043AB B203                <1> 	MOV	DL,3			; BYTES/SECTOR PARAMETER FROM BLOCK
  2005 000043AD E827020000          <1> 	CALL	GET_PARM 		; ... TO THE NEC
  2006 000043B2 E828030000          <1> 	CALL	NEC_OUTPUT		; OUTPUT TO CONTROLLER
  2007 000043B7 B204                <1> 	MOV	DL,4			; EOT PARAMETER FROM BLOCK
  2008 000043B9 E81B020000          <1> 	CALL	GET_PARM 		; ... TO THE NEC
  2009 000043BE E81C030000          <1> 	CALL	NEC_OUTPUT		; OUTPUT TO CONTROLLER
  2010 000043C3 8A6305              <1>         MOV     AH, [eBX+MD.GAP]        ; GET GAP LENGTH
  2011                              <1> _R15:
  2012 000043C6 E814030000          <1> 	CALL	NEC_OUTPUT
  2013 000043CB B206                <1> 	MOV	DL,6			; DTL PARAMETER PROM BLOCK
  2014 000043CD E807020000          <1> 	CALL	GET_PARM		;  TO THE NEC
  2015 000043D2 E808030000          <1> 	CALL	NEC_OUTPUT		; OUTPUT TO CONTROLLER
  2016 000043D7 58                  <1> 	POP	eAX			; THROW AWAY ERROR EXIT
  2017                              <1> ER_2:
  2018 000043D8 C3                  <1> 	RETn
  2019                              <1> 
  2020                              <1> ;-------------------------------------------------------------------------------
  2021                              <1> ; NEC_TERM
  2022                              <1> ;	THIS ROUTINE WAITS FOR THE OPERATION THEN ACCEPTS THE STATUS 
  2023                              <1> ;	FROM THE NEC FOR THE READ/WRITE/VERIFY/FORWAT OPERATION.
  2024                              <1> ;
  2025                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  2026                              <1> ;-------------------------------------------------------------------------------
  2027                              <1> NEC_TERM:
  2028                              <1> 
  2029                              <1> ;-----	LET THE OPERATION HAPPEN
  2030                              <1> 
  2031 000043D9 56                  <1> 	PUSH	eSI			; SAVE HEAD #, # OF SECTORS
  2032 000043DA E80D040000          <1> 	CALL	WAIT_INT		; WAIT FOR THE INTERRUPT
  2033 000043DF 9C                  <1> 	PUSHF
  2034 000043E0 E837040000          <1> 	CALL	RESULTS			; GET THE NEC STATUS
  2035 000043E5 724B                <1> 	JC	short SET_END_POP
  2036 000043E7 9D                  <1> 	POPF
  2037 000043E8 723E                <1> 	JC	short SET_END		; LOOK FOR ERROR
  2038                              <1> 
  2039                              <1> ;-----	CHECK THE RESULTS RETURNED BY THE CONTROLLER
  2040                              <1> 
  2041 000043EA FC                  <1> 	CLD				; SET THE CORRECT DIRECTION
  2042 000043EB BE[095F0100]        <1> 	MOV	eSI, NEC_STATUS		; POINT TO STATUS FIELD
  2043 000043F0 AC                  <1> 	lodsb				; GET ST0
  2044 000043F1 24C0                <1> 	AND	AL,11000000B		; TEST FOR NORMAL TERMINATION
  2045 000043F3 7433                <1> 	JZ	short SET_END
  2046 000043F5 3C40                <1> 	CMP	AL,01000000B		; TEST FOR ABNORMAL TERMINATION
  2047 000043F7 7527                <1> 	JNZ	short J18		; NOT ABNORMAL, BAD NEC
  2048                              <1> 
  2049                              <1> ;-----	ABNORMAL TERMINATION, FIND OUT WHY
  2050                              <1> 
  2051 000043F9 AC                  <1> 	lodsb				; GET ST1
  2052 000043FA D0E0                <1> 	SAL	AL,1			; TEST FOR EDT FOUND
  2053 000043FC B404                <1> 	MOV	AH,RECORD_NOT_FND
  2054 000043FE 7222                <1> 	JC	short J19
  2055 00004400 C0E002              <1> 	SAL	AL,2
  2056 00004403 B410                <1> 	MOV	AH,BAD_CRC
  2057 00004405 721B                <1> 	JC	short J19
  2058 00004407 D0E0                <1> 	SAL	AL,1			; TEST FOR DMA OVERRUN
  2059 00004409 B408                <1> 	MOV	AH,BAD_DMA
  2060 0000440B 7215                <1> 	JC	short J19
  2061 0000440D C0E002              <1> 	SAL	AL,2			; TEST FOR RECORD NOT FOUND
  2062 00004410 B404                <1> 	MOV	AH,RECORD_NOT_FND
  2063 00004412 720E                <1> 	JC	short J19
  2064 00004414 D0E0                <1> 	SAL	AL,1
  2065 00004416 B403                <1> 	MOV	AH,WRITE_PROTECT	; TEST FOR WRITE_PROTECT
  2066 00004418 7208                <1> 	JC	short J19
  2067 0000441A D0E0                <1> 	SAL	AL,1			; TEST MISSING ADDRESS MARK
  2068 0000441C B402                <1> 	MOV	AH,BAD_ADDR_MARK
  2069 0000441E 7202                <1> 	JC	short J19
  2070                              <1> 
  2071                              <1> ;----- 	NEC MUST HAVE FAILED
  2072                              <1> J18:
  2073 00004420 B420                <1> 	MOV	AH,BAD_NEC
  2074                              <1> J19:
  2075 00004422 0825[085F0100]      <1> 	OR	[DSKETTE_STATUS], AH
  2076                              <1> SET_END:
  2077 00004428 803D[085F0100]01    <1> 	CMP	byte [DSKETTE_STATUS], 1 ; SET ERROR CONDITION
  2078 0000442F F5                  <1> 	CMC
  2079 00004430 5E                  <1> 	POP	eSI
  2080 00004431 C3                  <1> 	RETn				; RESTORE HEAD #, # OF SECTORS
  2081                              <1> 
  2082                              <1> SET_END_POP:
  2083 00004432 9D                  <1> 	POPF
  2084 00004433 EBF3                <1> 	JMP	SHORT SET_END
  2085                              <1> 
  2086                              <1> ;-------------------------------------------------------------------------------
  2087                              <1> ; DSTATE:	ESTABLISH STATE UPON SUCCESSFUL OPERATION.
  2088                              <1> ;-------------------------------------------------------------------------------
  2089                              <1> DSTATE:
  2090 00004435 803D[085F0100]00    <1> 	CMP	byte [DSKETTE_STATUS],0	; CHECK FOR ERROR
  2091 0000443C 753E                <1> 	JNZ	short SETBAC		    ; IF ERROR JUMP
  2092 0000443E 808F[155F0100]10    <1> 	OR	byte [DSK_STATE+eDI],MED_DET ; NO ERROR, MARK MEDIA AS DETERMINED
  2093 00004445 F687[155F0100]04    <1> 	TEST	byte [DSK_STATE+eDI],DRV_DET ; DRIVE DETERMINED ?
  2094 0000444C 752E                <1> 	JNZ	short SETBAC		; IF DETERMINED NO TRY TO DETERMINE
  2095 0000444E 8A87[155F0100]      <1> 	MOV	AL,[DSK_STATE+eDI]	; LOAD STATE
  2096 00004454 24C0                <1> 	AND	AL,RATE_MSK		; KEEP ONLY RATE
  2097 00004456 3C80                <1> 	CMP	AL,RATE_250		; RATE 250 ?
  2098 00004458 751B                <1> 	JNE	short M_12		; NO, MUST BE 1.2M OR 1.44M DRIVE
  2099                              <1> 
  2100                              <1> ;----- 	CHECK IF IT IS 1.44M
  2101                              <1> 
  2102 0000445A E871010000          <1> 	CALL	CMOS_TYPE		; RETURN DRIVE TYPE IN (AL)
  2103                              <1> 	;;20/02/2015
  2104                              <1> 	;;JC	short M_12		; CMOS BAD
  2105 0000445F 7414                <1> 	jz	short M_12 ;; 20/02/2015
  2106 00004461 3C04                <1> 	CMP	AL, 4			; 1.44MB DRIVE ?
  2107 00004463 7410                <1> 	JE	short M_12		; YES
  2108                              <1> M_720:
  2109 00004465 80A7[155F0100]FD    <1> 	AND	byte [DSK_STATE+eDI], ~FMT_CAPA ; TURN OFF FORMAT CAPABILITY
  2110 0000446C 808F[155F0100]04    <1> 	OR	byte [DSK_STATE+eDI],DRV_DET  ; MARK DRIVE DETERMINED
  2111 00004473 EB07                <1> 	JMP	SHORT SETBAC		; BACK
  2112                              <1> M_12:	
  2113 00004475 808F[155F0100]06    <1> 	OR	byte [DSK_STATE+eDI],DRV_DET+FMT_CAPA 
  2114                              <1> 					; TURN ON DETERMINED & FMT CAPA
  2115                              <1> SETBAC:
  2116 0000447C C3                  <1> 	RETn
  2117                              <1> 
  2118                              <1> ;-------------------------------------------------------------------------------
  2119                              <1> ; RETRY	
  2120                              <1> ;	DETERMINES WHETHER A RETRY IS NECESSARY. 
  2121                              <1> ;	IF RETRY IS REQUIRED THEN STATE INFORMATION IS UPDATED FOR RETRY.
  2122                              <1> ;
  2123                              <1> ; ON EXIT:	CY = 1 FOR RETRY, CY = 0 FOR NO RETRY
  2124                              <1> ;-------------------------------------------------------------------------------
  2125                              <1> RETRY:
  2126 0000447D 803D[085F0100]00    <1> 	CMP	byte [DSKETTE_STATUS],0	; GET STATUS OF OPERATION
  2127 00004484 7445                <1> 	JZ	short NO_RETRY		; SUCCESSFUL OPERATION
  2128 00004486 803D[085F0100]80    <1> 	CMP	byte [DSKETTE_STATUS],TIME_OUT ; IF TIME OUT NO RETRY
  2129 0000448D 743C                <1> 	JZ	short NO_RETRY
  2130 0000448F 8AA7[155F0100]      <1> 	MOV	AH,[DSK_STATE+eDI]	; GET MEDIA STATE OF DRIVE
  2131 00004495 F6C410              <1> 	TEST	AH,MED_DET		; ESTABLISHED/DETERMINED ?
  2132 00004498 7531                <1> 	JNZ	short NO_RETRY		; IF ESTABLISHED STATE THEN TRUE ERROR
  2133 0000449A 80E4C0              <1> 	AND	AH,RATE_MSK		; ISOLATE RATE
  2134 0000449D 8A2D[105F0100]      <1> 	MOV	CH,[LASTRATE]		; GET START OPERATION STATE
  2135 000044A3 C0C504              <1> 	ROL	CH,4			; TO CORRESPONDING BITS
  2136 000044A6 80E5C0              <1> 	AND	CH,RATE_MSK		; ISOLATE RATE BITS
  2137 000044A9 38E5                <1> 	CMP	CH,AH			; ALL RATES TRIED
  2138 000044AB 741E                <1> 	JE	short NO_RETRY		; IF YES, THEN TRUE ERROR
  2139                              <1> 
  2140                              <1> ;	SETUP STATE INDICATOR FOR RETRY ATTEMPT TO NEXT RATE
  2141                              <1> ;	 00000000B (500) -> 10000000B	(250)
  2142                              <1> ;	 10000000B (250) -> 01000000B	(300)
  2143                              <1> ;	 01000000B (300) -> 00000000B	(500)
  2144                              <1> 
  2145 000044AD 80FC01              <1> 	CMP	AH,RATE_500+1		; SET CY FOR RATE 500
  2146 000044B0 D0DC                <1> 	RCR	AH,1			; TO NEXT STATE
  2147 000044B2 80E4C0              <1> 	AND	AH,RATE_MSK		; KEEP ONLY RATE BITS
  2148 000044B5 80A7[155F0100]1F    <1> 	AND	byte [DSK_STATE+eDI], ~(RATE_MSK+DBL_STEP)
  2149                              <1> 					; RATE, DBL STEP OFF
  2150 000044BC 08A7[155F0100]      <1> 	OR	[DSK_STATE+eDI],AH	; TURN ON NEW RATE
  2151 000044C2 C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS],0	; RESET STATUS FOR RETRY
  2152 000044C9 F9                  <1> 	STC				; SET CARRY FOR RETRY
  2153 000044CA C3                  <1> 	RETn				; RETRY RETURN
  2154                              <1> 
  2155                              <1> NO_RETRY:
  2156 000044CB F8                  <1> 	CLC				; CLEAR CARRY NO RETRY
  2157 000044CC C3                  <1> 	RETn				; NO RETRY RETURN
  2158                              <1> 
  2159                              <1> ;-------------------------------------------------------------------------------
  2160                              <1> ; NUM_TRANS
  2161                              <1> ;	THIS ROUTINE CALCULATES THE NUMBER OF SECTORS THAT WERE
  2162                              <1> ;	ACTUALLY TRANSFERRED TO/FROM THE DISKETTE.
  2163                              <1> ;
  2164                              <1> ; ON ENTRY:	[BP+1] = TRACK
  2165                              <1> ;		SI-HI  = HEAD
  2166                              <1> ;		[BP]   = START SECTOR
  2167                              <1> ;
  2168                              <1> ; ON EXIT:	AL = NUMBER ACTUALLY TRANSFERRED
  2169                              <1> ;-------------------------------------------------------------------------------
  2170                              <1> NUM_TRANS:
  2171 000044CD 30C0                <1> 	XOR	AL,AL			; CLEAR FOR ERROR
  2172 000044CF 803D[085F0100]00    <1> 	CMP	byte [DSKETTE_STATUS],0	; CHECK FOR ERROR
  2173 000044D6 752C                <1> 	JNZ	NT_OUT			; IF ERROR 0 TRANSFERRED
  2174 000044D8 B204                <1> 	MOV	DL,4			; SECTORS/TRACK OFFSET TO DL
  2175 000044DA E8FA000000          <1> 	CALL	GET_PARM		; AH = SECTORS/TRACK
  2176 000044DF 8A1D[0E5F0100]      <1> 	MOV	BL, [NEC_STATUS+5]	; GET ENDING SECTOR
  2177 000044E5 6689F1              <1> 	MOV	CX,SI			; CH = HEAD # STARTED
  2178 000044E8 3A2D[0D5F0100]      <1> 	CMP	CH, [NEC_STATUS+4]	; GET HEAD ENDED UP ON
  2179 000044EE 750D                <1> 	JNZ	DIF_HD			; IF ON SAME HEAD, THEN NO ADJUST
  2180 000044F0 8A2D[0C5F0100]      <1> 	MOV	CH, [NEC_STATUS+3]	; GET TRACK ENDED UP ON
  2181 000044F6 3A6D01              <1> 	CMP	CH,[eBP+1]		; IS IT ASKED FOR TRACK
  2182 000044F9 7404                <1> 	JZ	short SAME_TRK		; IF SAME TRACK NO INCREASE
  2183 000044FB 00E3                <1> 	ADD	BL,AH			; ADD SECTORS/TRACK
  2184                              <1> DIF_HD:
  2185 000044FD 00E3                <1> 	ADD	BL,AH			; ADD SECTORS/TRACK
  2186                              <1> SAME_TRK:
  2187 000044FF 2A5D00              <1> 	SUB	BL,[eBP]		; SUBTRACT START FROM END
  2188 00004502 88D8                <1> 	MOV	AL,BL			; TO AL
  2189                              <1> NT_OUT:
  2190 00004504 C3                  <1> 	RETn
  2191                              <1> 
  2192                              <1> ;-------------------------------------------------------------------------------
  2193                              <1> ; SETUP_END
  2194                              <1> ;	RESTORES @MOTOR_COUNT TO PARAMETER PROVIDED IN TABLE 
  2195                              <1> ;	AND LOADS @DSKETTE_STATUS TO AH, AND SETS CY.
  2196                              <1> ;
  2197                              <1> ; ON EXIT:
  2198                              <1> ;	AH, @DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  2199                              <1> ;-------------------------------------------------------------------------------
  2200                              <1> SETUP_END:
  2201 00004505 B202                <1> 	MOV	DL,2			; GET THE MOTOR WAIT PARAMETER
  2202 00004507 6650                <1> 	PUSH	AX			; SAVE NUMBER TRANSFERRED
  2203 00004509 E8CB000000          <1> 	CALL	GET_PARM
  2204 0000450E 8825[075F0100]      <1> 	MOV	[MOTOR_COUNT],AH	; STORE UPON RETURN
  2205 00004514 6658                <1> 	POP	AX			; RESTORE NUMBER TRANSFERRED
  2206 00004516 8A25[085F0100]      <1> 	MOV	AH, [DSKETTE_STATUS]	; GET STATUS OF OPERATION
  2207 0000451C 08E4                <1> 	OR	AH,AH			; CHECK FOR ERROR
  2208 0000451E 7402                <1> 	JZ	short NUN_ERR		; NO ERROR
  2209 00004520 30C0                <1> 	XOR	AL,AL			; CLEAR NUMBER RETURNED
  2210                              <1> NUN_ERR: 
  2211 00004522 80FC01              <1> 	CMP	AH,1			; SET THE CARRY FLAG TO INDICATE
  2212 00004525 F5                  <1> 	CMC				; SUCCESS OR FAILURE
  2213 00004526 C3                  <1> 	RETn
  2214                              <1> 
  2215                              <1> ;-------------------------------------------------------------------------------
  2216                              <1> ; SETUP_DBL
  2217                              <1> ;	CHECK DOUBLE STEP.
  2218                              <1> ;
  2219                              <1> ; ON ENTRY :	DI = DRIVE
  2220                              <1> ;
  2221                              <1> ; ON EXIT :	CY = 1 MEANS ERROR
  2222                              <1> ;-------------------------------------------------------------------------------
  2223                              <1> SETUP_DBL:
  2224 00004527 8AA7[155F0100]      <1> 	MOV	AH, [DSK_STATE+eDI]	; ACCESS STATE
  2225 0000452D F6C410              <1> 	TEST	AH,MED_DET		; ESTABLISHED STATE ?
  2226 00004530 757E                <1> 	JNZ	short NO_DBL			; IF ESTABLISHED THEN DOUBLE DONE
  2227                              <1> 
  2228                              <1> ;-----	CHECK FOR TRACK 0 TO SPEED UP ACKNOWLEDGE OF UNFORMATTED DISKETTE
  2229                              <1> 
  2230 00004532 C605[055F0100]00    <1> 	MOV	byte [SEEK_STATUS],0	; SET RECALIBRATE REQUIRED ON ALL DRIVES
  2231 00004539 E8E0000000          <1> 	CALL	MOTOR_ON		; ENSURE MOTOR STAY ON
  2232 0000453E B500                <1> 	MOV	CH,0			; LOAD TRACK 0
  2233 00004540 E8D4010000          <1> 	CALL	SEEK			; SEEK TO TRACK 0
  2234 00004545 E868000000          <1> 	CALL	READ_ID			; READ ID FUNCTION
  2235 0000454A 7249                <1> 	JC	short SD_ERR		; IF ERROR NO TRACK 0
  2236                              <1> 
  2237                              <1> ;-----	INITIALIZE START AND MAX TRACKS (TIMES 2 FOR BOTH HEADS)
  2238                              <1> 
  2239 0000454C 66B95004            <1> 	MOV	CX,0450H 		; START, MAX TRACKS
  2240 00004550 F687[155F0100]01    <1> 	TEST	byte [DSK_STATE+eDI],TRK_CAPA ; TEST FOR 80 TRACK CAPABILITY
  2241 00004557 7402                <1> 	JZ	short CNT_OK		; IF NOT COUNT IS SETUP
  2242 00004559 B1A0                <1> 	MOV	CL,0A0H			; MAXIMUM TRACK 1.2 MB
  2243                              <1> 
  2244                              <1> ;	ATTEMPT READ ID OF ALL TRACKS, ALL HEADS UNTIL SUCCESS; UPON SUCCESS,
  2245                              <1> ;	MUST SEE IF ASKED FOR TRACK IN SINGLE STEP MODE = TRACK ID READ; IF NOT
  2246                              <1> ;	THEN SET DOUBLE STEP ON.
  2247                              <1> 
  2248                              <1> CNT_OK:
  2249 0000455B C605[075F0100]FF    <1>         MOV     byte [MOTOR_COUNT], 0FFH ; ENSURE MOTOR STAYS ON FOR OPERATION 
  2250 00004562 6651                <1> 	PUSH	CX			; SAVE TRACK, COUNT
  2251 00004564 C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS],0	; CLEAR STATUS, EXPECT ERRORS
  2252 0000456B 6631C0              <1> 	XOR	AX,AX			; CLEAR AX
  2253 0000456E D0ED                <1> 	SHR	CH,1			; HALVE TRACK, CY = HEAD
  2254 00004570 C0D003              <1> 	RCL	AL,3			; AX = HEAD IN CORRECT BIT
  2255 00004573 6650                <1> 	PUSH	AX			; SAVE HEAD
  2256 00004575 E89F010000          <1> 	CALL	SEEK			; SEEK TO TRACK
  2257 0000457A 6658                <1> 	POP	AX			; RESTORE HEAD
  2258 0000457C 6609C7              <1> 	OR	DI,AX			; DI = HEAD OR'ED DRIVE
  2259 0000457F E82E000000          <1> 	CALL	READ_ID			; READ ID HEAD 0
  2260 00004584 9C                  <1> 	PUSHF				; SAVE RETURN FROM READ_ID
  2261 00004585 6681E7FB00          <1> 	AND	DI,11111011B		; TURN OFF HEAD 1 BIT
  2262 0000458A 9D                  <1> 	POPF				; RESTORE ERROR RETURN
  2263 0000458B 6659                <1> 	POP	CX			; RESTORE COUNT
  2264 0000458D 7308                <1> 	JNC	short DO_CHK		; IF OK, ASKED = RETURNED TRACK ?
  2265 0000458F FEC5                <1> 	INC	CH			; INC FOR NEXT TRACK
  2266 00004591 38CD                <1> 	CMP	CH,CL			; REACHED MAXIMUM YET
  2267 00004593 75C6                <1> 	JNZ	short CNT_OK		; CONTINUE TILL ALL TRIED
  2268                              <1> 
  2269                              <1> ;-----	FALL THRU, READ ID FAILED FOR ALL TRACKS
  2270                              <1> 
  2271                              <1> SD_ERR:	
  2272 00004595 F9                  <1> 	STC				; SET CARRY FOR ERROR
  2273 00004596 C3                  <1> 	RETn				; SETUP_DBL ERROR EXIT
  2274                              <1> 
  2275                              <1> DO_CHK:
  2276 00004597 8A0D[0C5F0100]      <1> 	MOV	CL, [NEC_STATUS+3]	; LOAD RETURNED TRACK
  2277 0000459D 888F[195F0100]      <1> 	MOV	[DSK_TRK+eDI], CL	; STORE TRACK NUMBER
  2278 000045A3 D0ED                <1> 	SHR	CH,1			; HALVE TRACK
  2279 000045A5 38CD                <1> 	CMP	CH,CL			; IS IT THE SAME AS ASKED FOR TRACK
  2280 000045A7 7407                <1> 	JZ	short NO_DBL		; IF SAME THEN NO DOUBLE STEP
  2281 000045A9 808F[155F0100]20    <1> 	OR	byte [DSK_STATE+eDI],DBL_STEP ; TURN ON DOUBLE STEP REQUIRED
  2282                              <1> NO_DBL:
  2283 000045B0 F8                  <1> 	CLC				; CLEAR ERROR FLAG
  2284 000045B1 C3                  <1> 	RETn
  2285                              <1> 
  2286                              <1> ;-------------------------------------------------------------------------------
  2287                              <1> ; READ_ID
  2288                              <1> ;	READ ID FUNCTION.
  2289                              <1> ;
  2290                              <1> ; ON ENTRY:	DI : BIT 2 = HEAD; BITS 1,0 = DRIVE
  2291                              <1> ;
  2292                              <1> ; ON EXIT: 	DI : BIT 2 IS RESET, BITS 1,0 = DRIVE
  2293                              <1> ;		@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION
  2294                              <1> ;-------------------------------------------------------------------------------
  2295                              <1> READ_ID:
  2296 000045B2 B8[CF450000]        <1> 	MOV	eAX, ER_3		; MOVE NEC OUTPUT ERROR ADDRESS
  2297 000045B7 50                  <1> 	PUSH	eAX
  2298 000045B8 B44A                <1> 	MOV	AH,4AH			; READ ID COMMAND
  2299 000045BA E820010000          <1> 	CALL	NEC_OUTPUT		; TO CONTROLLER
  2300 000045BF 6689F8              <1> 	MOV	AX,DI			; DRIVE # TO AH, HEAD 0
  2301 000045C2 88C4                <1> 	MOV	AH,AL
  2302 000045C4 E816010000          <1> 	CALL	NEC_OUTPUT		; TO CONTROLLER
  2303 000045C9 E80BFEFFFF          <1> 	CALL	NEC_TERM		; WAIT FOR OPERATION, GET STATUS
  2304 000045CE 58                  <1> 	POP	eAX			; THROW AWAY ERROR ADDRESS
  2305                              <1> ER_3:
  2306 000045CF C3                  <1> 	RETn
  2307                              <1> 
  2308                              <1> ;-------------------------------------------------------------------------------
  2309                              <1> ; CMOS_TYPE
  2310                              <1> ;	RETURNS DISKETTE TYPE FROM CMOS
  2311                              <1> ;
  2312                              <1> ; ON ENTRY:	DI = DRIVE #
  2313                              <1> ;
  2314                              <1> ; ON EXIT:	AL = TYPE; CY REFLECTS STATUS
  2315                              <1> ;-------------------------------------------------------------------------------
  2316                              <1> 
  2317                              <1> CMOS_TYPE: ; 11/12/2014
  2318 000045D0 8A87[AE640000]      <1> mov	al, [eDI+fd0_type]
  2319 000045D6 20C0                <1> and 	al, al ; 18/12/2014
  2320 000045D8 C3                  <1> retn
  2321                              <1> 
  2322                              <1> ;CMOS_TYPE:
  2323                              <1> ;	MOV	AL, CMOS_DIAG		; CMOS DIAGNOSTIC STATUS BYTE ADDRESS
  2324                              <1> ;	CALL	CMOS_READ		; GET CMOS STATUS
  2325                              <1> ;	TEST	AL,BAD_BAT+BAD_CKSUM	; BATTERY GOOD AND CHECKSUM VALID
  2326                              <1> ;	STC				; SET CY = 1 INDICATING ERROR FOR RETURN
  2327                              <1> ;	JNZ	short BAD_CM		; ERROR IF EITHER BIT ON
  2328                              <1> ;	MOV	AL,CMOS_DISKETTE	; ADDRESS OF DISKETTE BYTE IN CMOS
  2329                              <1> ;	CALL	CMOS_READ		; GET DISKETTE BYTE
  2330                              <1> ;	OR	DI,DI			; SEE WHICH DRIVE IN QUESTION
  2331                              <1> ;	JNZ	short TB		; IF DRIVE 1, DATA IN LOW NIBBLE
  2332                              <1> ;	ROR	AL,4			; EXCHANGE NIBBLES IF SECOND DRIVE
  2333                              <1> ;TB:
  2334                              <1> ;	AND	AL,0FH			; KEEP ONLY DRIVE DATA, RESET CY, 0
  2335                              <1> ;BAD_CM:
  2336                              <1> ;	RETn				; CY, STATUS OF READ
  2337                              <1> 
  2338                              <1> ;-------------------------------------------------------------------------------
  2339                              <1> ; GET_PARM
  2340                              <1> ;	THIS ROUTINE FETCHES THE INDEXED POINTER FROM THE DISK_BASE
  2341                              <1> ;	BLOCK POINTED TO BY THE DATA VARIABLE @DISK_POINTER. A BYTE FROM
  2342                              <1> ;	THAT TABLE IS THEN MOVED INTO AH, THE INDEX OF THAT BYTE BEING
  2343                              <1> ;	THE PARAMETER IN DL.
  2344                              <1> ;
  2345                              <1> ; ON ENTRY:	DL = INDEX OF BYTE TO BE FETCHED
  2346                              <1> ;
  2347                              <1> ; ON EXIT:	AH = THAT BYTE FROM BLOCK
  2348                              <1> ;		AL,DH DESTROYED
  2349                              <1> ;-------------------------------------------------------------------------------
  2350                              <1> GET_PARM:
  2351                              <1> 	;PUSH	DS
  2352 000045D9 56                  <1> 	PUSH	eSI
  2353                              <1>     	;SUB	AX,AX			; DS = 0, BIOS DATA AREA
  2354                              <1>     	;MOV	DS,AX
  2355                              <1> 	;;mov	ax, cs
  2356                              <1> 	;;mov	ds, ax
  2357                              <1> 	; 08/02/2015 (protected mode modifications, bx -> ebx)
  2358 000045DA 87D3                <1> 	XCHG	eDX,eBX			; BL = INDEX
  2359                              <1> 	;SUB	BH,BH			; BX = INDEX
  2360 000045DC 81E3FF000000        <1> 	and	ebx, 0FFh
  2361                              <1>     	;LDS	SI, [DISK_POINTER]	; POINT TO BLOCK
  2362                              <1> 	;
  2363                              <1> 	; 17/12/2014
  2364 000045E2 66A1[9D640000]      <1> 	mov	ax, [cfd] ; current (AL) and previous fd (AH)
  2365 000045E8 38E0                <1> 	cmp	al, ah
  2366 000045EA 7425                <1> 	je	short gpndc
  2367 000045EC A2[9E640000]        <1> 	mov	[pfd], al ; current drive -> previous drive
  2368 000045F1 53                  <1> 	push	ebx ; 08/02/2015
  2369 000045F2 88C3                <1> 	mov	bl, al 
  2370                              <1> 	; 11/12/2014
  2371 000045F4 8A83[AE640000]      <1> 	mov	al, [eBX+fd0_type]	; Drive type (0,1,2,3,4)
  2372                              <1> 	; 18/12/2014
  2373 000045FA 20C0                <1> 	and	al, al
  2374 000045FC 7507                <1> 	jnz	short gpdtc
  2375 000045FE BB[87640000]        <1> 	mov	ebx, MD_TBL6		; 1.44 MB param. tbl. (default)
  2376 00004603 EB05                <1>         jmp     short gpdpu
  2377                              <1> gpdtc:	
  2378 00004605 E817F9FFFF          <1> 	call	DR_TYPE_CHECK
  2379                              <1> 	; cf = 1 -> eBX points to 1.44MB fd parameter table (default)
  2380                              <1> gpdpu:
  2381 0000460A 891D[24640000]      <1> 	mov	[DISK_POINTER], ebx
  2382 00004610 5B                  <1> 	pop	ebx
  2383                              <1> gpndc:
  2384 00004611 8B35[24640000]      <1> 	mov	esi, [DISK_POINTER] ; 08/02/2015, si -> esi
  2385 00004617 8A241E              <1> 	MOV	AH, [eSI+eBX]		; GET THE WORD
  2386 0000461A 87D3                <1> 	XCHG	eDX,eBX			; RESTORE BX
  2387 0000461C 5E                  <1> 	POP	eSI
  2388                              <1> 	;POP	DS
  2389 0000461D C3                  <1> 	RETn
  2390                              <1> 
  2391                              <1> ;-------------------------------------------------------------------------------
  2392                              <1> ; MOTOR_ON
  2393                              <1> ;	TURN MOTOR ON AND WAIT FOR MOTOR START UP TIME. THE @MOTOR_COUNT
  2394                              <1> ;	IS REPLACED WITH A SUFFICIENTLY HIGH NUMBER (0FFH) TO ENSURE
  2395                              <1> ;	THAT THE MOTOR DOES NOT GO OFF DURING THE OPERATION. IF THE
  2396                              <1> ;	MOTOR NEEDED TO BE TURNED ON, THE MULTI-TASKING HOOK FUNCTION
  2397                              <1> ;	(AX=90FDH, INT 15) IS CALLED TELLING THE OPERATING SYSTEM
  2398                              <1> ;	THAT THE BIOS IS ABOUT TO WAIT FOR MOTOR START UP. IF THIS
  2399                              <1> ;	FUNCTION RETURNS WITH CY = 1, IT MEANS THAT THE MINIMUM WAIT
  2400                              <1> ;	HAS BEEN COMPLETED. AT THIS POINT A CHECK IS MADE TO ENSURE
  2401                              <1> ;	THAT THE MOTOR WASN'T TURNED OFF BY THE TIMER. IF THE HOOK DID
  2402                              <1> ;	NOT WAIT, THE WAIT FUNCTION (AH=086H) IS CALLED TO WAIT THE
  2403                              <1> ;	PRESCRIBED AMOUNT OF TIME. IF THE CARRY FLAG IS SET ON RETURN,
  2404                              <1> ;	IT MEANS THAT THE FUNCTION IS IN USE AND DID NOT PERFORM THE
  2405                              <1> ;	WAIT. A TIMER 1 WAIT LOOP WILL THEN DO THE WAIT.
  2406                              <1> ;
  2407                              <1> ; ON ENTRY:	DI = DRIVE #
  2408                              <1> ; ON EXIT:	AX,CX,DX DESTROYED
  2409                              <1> ;-------------------------------------------------------------------------------
  2410                              <1> MOTOR_ON:
  2411 0000461E 53                  <1> 	PUSH	eBX			; SAVE REG.
  2412 0000461F E82A000000          <1> 	CALL	TURN_ON			; TURN ON MOTOR
  2413 00004624 7226                <1> 	JC	short MOT_IS_ON		; IF CY=1 NO WAIT
  2414 00004626 E89BF9FFFF          <1> 	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  2415 0000462B E865F9FFFF          <1> 	CALL	XLAT_NEW		; TRANSLATE STATE TO PRESENT ARCH,
  2416                              <1> 	;CALL	TURN_ON 		; CHECK AGAIN IF MOTOR ON
  2417                              <1> 	;JC	MOT_IS_ON		; IF NO WAIT MEANS IT IS ON
  2418                              <1> M_WAIT:
  2419 00004630 B20A                <1> 	MOV	DL,10			; GET THE MOTOR WAIT PARAMETER
  2420 00004632 E8A2FFFFFF          <1> 	CALL	GET_PARM
  2421                              <1> 	;MOV	AL,AH			; AL = MOTOR WAIT PARAMETER
  2422                              <1> 	;XOR	AH,AH			; AX = MOTOR WAIT PARAMETER
  2423                              <1> 	;CMP	AL,8			; SEE IF AT LEAST A SECOND IS SPECIFIED
  2424 00004637 80FC08              <1> 	cmp	ah, 8
  2425                              <1> 	;JAE	short GP2		; IF YES, CONTINUE
  2426 0000463A 7702                <1> 	ja	short J13
  2427                              <1> 	;MOV	AL,8			; ONE SECOND WAIT FOR MOTOR START UP
  2428 0000463C B408                <1> 	mov	ah, 8
  2429                              <1> 
  2430                              <1> ;-----	AS CONTAINS NUMBER OF 1/8 SECONDS (125000 MICROSECONDS) TO WAIT
  2431                              <1> GP2:	
  2432                              <1> ;----- 	FOLLOWING LOOPS REQUIRED WHEN RTC WAIT FUNCTION IS ALREADY IN USE
  2433                              <1> J13:					; WAIT FOR 1/8 SECOND PER (AL)
  2434 0000463E B95E200000          <1> 	MOV	eCX,8286		; COUNT FOR 1/8 SECOND AT 15.085737 US
  2435 00004643 E8D0DBFFFF          <1> 	CALL	WAITF			; GO TO FIXED WAIT ROUTINE
  2436                              <1> 	;DEC	AL			; DECREMENT TIME VALUE
  2437 00004648 FECC                <1> 	dec	ah
  2438 0000464A 75F2                <1> 	JNZ	short J13		; ARE WE DONE YET
  2439                              <1> MOT_IS_ON:
  2440 0000464C 5B                  <1> 	POP	eBX			; RESTORE REG.
  2441 0000464D C3                  <1> 	RETn
  2442                              <1> 
  2443                              <1> ;-------------------------------------------------------------------------------
  2444                              <1> ; TURN_ON
  2445                              <1> ;	TURN MOTOR ON AND RETURN WAIT STATE.
  2446                              <1> ;
  2447                              <1> ; ON ENTRY:	DI = DRIVE #
  2448                              <1> ;
  2449                              <1> ; ON EXIT:	CY = 0 MEANS WAIT REQUIRED
  2450                              <1> ;		CY = 1 MEANS NO WAIT REQUIRED
  2451                              <1> ;		AX,BX,CX,DX DESTROYED
  2452                              <1> ;-------------------------------------------------------------------------------
  2453                              <1> TURN_ON:
  2454 0000464E 89FB                <1> 	MOV	eBX,eDI			; BX = DRIVE #
  2455 00004650 88D9                <1> 	MOV	CL,BL			; CL = DRIVE #
  2456 00004652 C0C304              <1> 	ROL	BL,4			; BL = DRIVE SELECT
  2457 00004655 FA                  <1> 	CLI				; NO INTERRUPTS WHILE DETERMINING STATUS
  2458 00004656 C605[075F0100]FF    <1> 	MOV	byte [MOTOR_COUNT],0FFH	; ENSURE MOTOR STAYS ON FOR OPERATION
  2459 0000465D A0[065F0100]        <1> 	MOV	AL, [MOTOR_STATUS]	; GET DIGITAL OUTPUT REGISTER REFLECTION
  2460 00004662 2430                <1> 	AND	AL,00110000B		; KEEP ONLY DRIVE SELECT BITS
  2461 00004664 B401                <1> 	MOV	AH,1			; MASK FOR DETERMINING MOTOR BIT
  2462 00004666 D2E4                <1> 	SHL	AH,CL			; AH = MOTOR ON, A=00000001, B=00000010
  2463                              <1> 
  2464                              <1> ;  AL = DRIVE SELECT FROM @MOTOR_STATUS
  2465                              <1> ;  BL = DRIVE SELECT DESIRED
  2466                              <1> ;  AH = MOTOR ON MASK DESIRED
  2467                              <1> 
  2468 00004668 38D8                <1> 	CMP	AL,BL			; REQUESTED DRIVE ALREADY SELECTED ?
  2469 0000466A 7508                <1> 	JNZ	short TURN_IT_ON	; IF NOT SELECTED JUMP
  2470 0000466C 8425[065F0100]      <1> 	TEST	AH, [MOTOR_STATUS]	; TEST MOTOR ON BIT
  2471 00004672 7535                <1> 	JNZ	short NO_MOT_WAIT	; JUMP IF MOTOR ON AND SELECTED
  2472                              <1> 
  2473                              <1> TURN_IT_ON:
  2474 00004674 08DC                <1> 	OR	AH,BL			; AH = DRIVE SELECT AND MOTOR ON
  2475 00004676 8A3D[065F0100]      <1> 	MOV	BH,[MOTOR_STATUS]	; SAVE COPY OF @MOTOR_STATUS BEFORE
  2476 0000467C 80E70F              <1> 	AND	BH,00001111B		; KEEP ONLY MOTOR BITS
  2477 0000467F 8025[065F0100]CF    <1> 	AND	byte [MOTOR_STATUS],11001111B ; CLEAR OUT DRIVE SELECT
  2478 00004686 0825[065F0100]      <1> 	OR	[MOTOR_STATUS],AH	; OR IN DRIVE SELECTED AND MOTOR ON
  2479 0000468C A0[065F0100]        <1> 	MOV	AL,[MOTOR_STATUS]	; GET DIGITAL OUTPUT REGISTER REFLECTION
  2480 00004691 88C3                <1> 	MOV	BL,AL			; BL=@MOTOR_STATUS AFTER, BH=BEFORE
  2481 00004693 80E30F              <1> 	AND	BL,00001111B		; KEEP ONLY MOTOR BITS
  2482 00004696 FB                  <1> 	STI				; ENABLE INTERRUPTS AGAIN
  2483 00004697 243F                <1> 	AND	AL,00111111B		; STRIP AWAY UNWANTED BITS
  2484 00004699 C0C004              <1> 	ROL	AL,4			; PUT BITS IN DESIRED POSITIONS
  2485 0000469C 0C0C                <1> 	OR	AL,00001100B		; NO RESET, ENABLE DMA/INTERRUPT
  2486 0000469E 66BAF203            <1> 	MOV	DX,03F2H		; SELECT DRIVE AND TURN ON MOTOR
  2487 000046A2 EE                  <1> 	OUT	DX,AL
  2488 000046A3 38FB                <1> 	CMP	BL,BH			; NEW MOTOR TURNED ON ?
  2489                              <1> 	;JZ	short NO_MOT_WAIT	; NO WAIT REQUIRED IF JUST SELECT
  2490 000046A5 7403                <1> 	je	short no_mot_w1 ; 27/02/2015 
  2491 000046A7 F8                  <1> 	CLC				; (re)SET CARRY MEANING WAIT
  2492 000046A8 C3                  <1> 	RETn
  2493                              <1> 
  2494                              <1> NO_MOT_WAIT:
  2495 000046A9 FB                  <1> 	sti
  2496                              <1> no_mot_w1: ; 27/02/2015
  2497 000046AA F9                  <1> 	STC				; SET NO WAIT REQUIRED
  2498                              <1> 	;STI				; INTERRUPTS BACK ON
  2499 000046AB C3                  <1> 	RETn
  2500                              <1> 
  2501                              <1> ;-------------------------------------------------------------------------------
  2502                              <1> ; HD_WAIT
  2503                              <1> ;	WAIT FOR HEAD SETTLE TIME.
  2504                              <1> ;
  2505                              <1> ; ON ENTRY:	DI = DRIVE #
  2506                              <1> ;
  2507                              <1> ; ON EXIT:	AX,BX,CX,DX DESTROYED
  2508                              <1> ;-------------------------------------------------------------------------------
  2509                              <1> HD_WAIT:
  2510 000046AC B209                <1> 	MOV	DL,9			; GET HEAD SETTLE PARAMETER
  2511 000046AE E826FFFFFF          <1> 	CALL	GET_PARM
  2512 000046B3 08E4                <1> 	or	ah, ah	; 17/12/2014
  2513 000046B5 7519                <1> 	jnz	short DO_WAT
  2514 000046B7 F605[065F0100]80    <1>         TEST    byte [MOTOR_STATUS],10000000B ; SEE IF A WRITE OPERATION
  2515                              <1> 	;JZ	short ISNT_WRITE	; IF NOT, DO NOT ENFORCE ANY VALUES
  2516                              <1> 	;OR	AH,AH			; CHECK FOR ANY WAIT?
  2517                              <1> 	;JNZ	short DO_WAT		; IF THERE DO NOT ENFORCE
  2518 000046BE 741E                <1> 	jz	short HW_DONE
  2519 000046C0 B40F                <1> 	MOV	AH,HD12_SETTLE		; LOAD 1.2M HEAD SETTLE MINIMUM
  2520 000046C2 8A87[155F0100]      <1> 	MOV	AL,[DSK_STATE+eDI]	; LOAD STATE
  2521 000046C8 24C0                <1> 	AND	AL,RATE_MSK		; KEEP ONLY RATE
  2522 000046CA 3C80                <1> 	CMP	AL,RATE_250		; 1.2 M DRIVE ?
  2523 000046CC 7502                <1> 	JNZ	short DO_WAT		; DEFAULT HEAD SETTLE LOADED
  2524                              <1> ;GP3:
  2525 000046CE B414                <1> 	MOV	AH,HD320_SETTLE		; USE 320/360 HEAD SETTLE
  2526                              <1> ;	JMP	SHORT DO_WAT
  2527                              <1> 
  2528                              <1> ;ISNT_WRITE:
  2529                              <1> ;	OR	AH,AH			; CHECK FOR NO WAIT
  2530                              <1> ;	JZ	short HW_DONE		; IF NOT WRITE AND 0 ITS OK
  2531                              <1> 
  2532                              <1> ;-----	AH CONTAINS NUMBER OF MILLISECONDS TO WAIT
  2533                              <1> DO_WAT:
  2534                              <1> ;	MOV	AL,AH			; AL = # MILLISECONDS
  2535                              <1> ;	;XOR	AH,AH			; AX = # MILLISECONDS
  2536                              <1> J29:					; 	1 MILLISECOND LOOP
  2537                              <1> 	;mov	cx, WAIT_FDU_HEAD_SETTLE ; 33 ; 1 ms in 30 micro units.
  2538 000046D0 B942000000          <1> 	MOV	eCX,66			; COUNT AT 15.085737 US PER COUNT
  2539 000046D5 E83EDBFFFF          <1> 	CALL	WAITF			; DELAY FOR 1 MILLISECOND
  2540                              <1> 	;DEC	AL			; DECREMENT THE COUNT
  2541 000046DA FECC                <1> 	dec	ah
  2542 000046DC 75F2                <1> 	JNZ	short J29		; DO AL MILLISECOND # OF TIMES
  2543                              <1> HW_DONE:
  2544 000046DE C3                  <1> 	RETn
  2545                              <1> 
  2546                              <1> ;-------------------------------------------------------------------------------
  2547                              <1> ; NEC_OUTPUT
  2548                              <1> ;	THIS ROUTINE SENDS A BYTE TO THE NEC CONTROLLER AFTER TESTING
  2549                              <1> ;	FOR CORRECT DIRECTION AND CONTROLLER READY THIS ROUTINE WILL
  2550                              <1> ;	TIME OUT IF THE BYTE IS NOT ACCEPTED WITHIN A REASONABLE AMOUNT
  2551                              <1> ;	OF TIME, SETTING THE DISKETTE STATUS ON COMPLETION.
  2552                              <1> ; 
  2553                              <1> ; ON ENTRY: 	AH = BYTE TO BE OUTPUT
  2554                              <1> ;
  2555                              <1> ; ON EXIT:	CY = 0  SUCCESS
  2556                              <1> ;		CY = 1  FAILURE -- DISKETTE STATUS UPDATED
  2557                              <1> ;		        IF A FAILURE HAS OCCURRED, THE RETURN IS MADE ONE LEVEL
  2558                              <1> ;		        HIGHER THAN THE CALLER OF NEC OUTPUT. THIS REMOVES THE
  2559                              <1> ;		        REQUIREMENT OF TESTING AFTER EVERY CALL OF NEC_OUTPUT.
  2560                              <1> ;		AX,CX,DX DESTROYED
  2561                              <1> ;-------------------------------------------------------------------------------
  2562                              <1> 
  2563                              <1> ; 09/12/2014 [Erdogan Tan] 
  2564                              <1> ;	(from 'PS2 Hardware Interface Tech. Ref. May 88', Page 09-05.)
  2565                              <1> ; Diskette Drive Controller Status Register (3F4h)
  2566                              <1> ;	This read only register facilitates the transfer of data between
  2567                              <1> ;	the system microprocessor and the controller.
  2568                              <1> ; Bit 7 - When set to 1, the Data register is ready to transfer data 
  2569                              <1> ;	  with the system micrprocessor.
  2570                              <1> ; Bit 6 - The direction of data transfer. If this bit is set to 0,
  2571                              <1> ;	  the transfer is to the controller.
  2572                              <1> ; Bit 5 - When this bit is set to 1, the controller is in the non-DMA mode.
  2573                              <1> ; Bit 4 - When this bit is set to 1, a Read or Write command is being executed.
  2574                              <1> ; Bit 3 - Reserved.
  2575                              <1> ; Bit 2 - Reserved.
  2576                              <1> ; Bit 1 - When this bit is set to 1, dskette drive 1 is in the seek mode.
  2577                              <1> ; Bit 0 - When this bit is set to 1, dskette drive 1 is in the seek mode.
  2578                              <1> 
  2579                              <1> ; Data Register (3F5h)
  2580                              <1> ; This read/write register passes data, commands and parameters, and provides
  2581                              <1> ; diskette status information.
  2582                              <1>   		
  2583                              <1> NEC_OUTPUT:
  2584                              <1> 	;PUSH	BX			; SAVE REG.
  2585 000046DF 66BAF403            <1> 	MOV	DX,03F4H		; STATUS PORT
  2586                              <1> 	;MOV	BL,2			; HIGH ORDER COUNTER
  2587                              <1> 	;XOR	CX,CX			; COUNT FOR TIME OUT
  2588                              <1> 	; 16/12/2014
  2589                              <1> 	; waiting for (max.) 0.5 seconds
  2590                              <1>         ;;mov     byte [wait_count], 0 ;; 27/02/2015
  2591                              <1> 	;
  2592                              <1> 	; 17/12/2014
  2593                              <1> 	; Modified from AWARD BIOS 1999 - ADISK.ASM - SEND_COMMAND
  2594                              <1> 	;
  2595                              <1> 	;WAIT_FOR_PORT:	Waits for a bit at a port pointed to by DX to
  2596                              <1> 	;		go on.
  2597                              <1> 	;INPUT:
  2598                              <1> 	;	AH=Mask for isolation bits.
  2599                              <1> 	;	AL=pattern to look for.
  2600                              <1> 	;	DX=Port to test for
  2601                              <1> 	;	BH:CX=Number of memory refresh periods to delay.
  2602                              <1> 	;	     (normally 30 microseconds per period.)
  2603                              <1> 	;
  2604                              <1> 	;WFP_SHORT:  
  2605                              <1> 	;	Wait for port if refresh cycle is short (15-80 Us range).
  2606                              <1> 	;
  2607                              <1> 
  2608                              <1> ;	mov	bl, WAIT_FDU_SEND_HI+1	; 0+1
  2609                              <1> ;	mov	cx, WAIT_FDU_SEND_LO	; 16667
  2610 000046E3 B91B410000          <1> 	mov	ecx, WAIT_FDU_SEND_LH   ; 16667 (27/02/2015)
  2611                              <1> ;
  2612                              <1> ;WFPS_OUTER_LP:
  2613                              <1> ;	;
  2614                              <1> ;WFPS_CHECK_PORT:
  2615                              <1> J23:
  2616 000046E8 EC                  <1> 	IN	AL,DX			; GET STATUS
  2617 000046E9 24C0                <1> 	AND	AL,11000000B		; KEEP STATUS AND DIRECTION
  2618 000046EB 3C80                <1> 	CMP	AL,10000000B		; STATUS 1 AND DIRECTION 0 ?
  2619 000046ED 7418                <1> 	JZ	short J27		; STATUS AND DIRECTION OK
  2620                              <1> WFPS_HI:
  2621 000046EF E461                <1> 	IN	AL, PORT_B	;061h	; SYS1	; wait for hi to lo
  2622 000046F1 A810                <1> 	TEST	AL,010H			; transition on memory
  2623 000046F3 75FA                <1> 	JNZ	SHORT WFPS_HI		; refresh.
  2624                              <1> WFPS_LO:
  2625 000046F5 E461                <1> 	IN	AL, PORT_B		; SYS1
  2626 000046F7 A810                <1> 	TEST	AL,010H
  2627 000046F9 74FA                <1> 	JZ	SHORT WFPS_LO
  2628                              <1> 	;LOOP	SHORT WFPS_CHECK_PORT
  2629 000046FB E2EB                <1> 	loop	J23	; 27/02/2015
  2630                              <1> ;	;
  2631                              <1> ;	dec	bl
  2632                              <1> ;	jnz	short WFPS_OUTER_LP
  2633                              <1> ;	jmp	short WFPS_TIMEOUT	; fail
  2634                              <1> ;J23:
  2635                              <1> ;	IN	AL,DX			; GET STATUS
  2636                              <1> ;	AND	AL,11000000B		; KEEP STATUS AND DIRECTION
  2637                              <1> ;	CMP	AL,10000000B		; STATUS 1 AND DIRECTION 0 ?
  2638                              <1> ;	JZ	short J27		; STATUS AND DIRECTION OK
  2639                              <1> 	;LOOP	J23			; CONTINUE TILL CX EXHAUSTED
  2640                              <1> 	;DEC	BL			; DECREMENT COUNTER
  2641                              <1> 	;JNZ	short J23		; REPEAT TILL DELAY FINISHED, CX = 0
  2642                              <1>    
  2643                              <1> 	;;27/02/2015
  2644                              <1> 	;16/12/2014
  2645                              <1>         ;;cmp     byte [wait_count], 10   ; (10/18.2 seconds)
  2646                              <1> 	;;jb	short J23
  2647                              <1> 
  2648                              <1> ;WFPS_TIMEOUT:
  2649                              <1> 
  2650                              <1> ;-----	FALL THRU TO ERROR RETURN
  2651                              <1> 
  2652 000046FD 800D[085F0100]80    <1> 	OR	byte [DSKETTE_STATUS],TIME_OUT
  2653                              <1> 	;POP	BX			; RESTORE REG.
  2654 00004704 58                  <1> 	POP	eAX ; 08/02/2015	; DISCARD THE RETURN ADDRESS
  2655 00004705 F9                  <1> 	STC				; INDICATE ERROR TO CALLER
  2656 00004706 C3                  <1> 	RETn
  2657                              <1> 
  2658                              <1> ;-----	DIRECTION AND STATUS OK; OUTPUT BYTE
  2659                              <1> 
  2660                              <1> J27:	
  2661 00004707 88E0                <1> 	MOV	AL,AH			; GET BYTE TO OUTPUT
  2662 00004709 6642                <1> 	INC	DX			; DATA PORT = STATUS PORT + 1
  2663 0000470B EE                  <1> 	OUT	DX,AL			; OUTPUT THE BYTE
  2664                              <1> 	;;NEWIODELAY  ;; 27/02/2015
  2665                              <1> 	; 27/02/2015
  2666 0000470C 9C                  <1> 	PUSHF				; SAVE FLAGS
  2667 0000470D B903000000          <1> 	MOV	eCX, 3			; 30 TO 45 MICROSECONDS WAIT FOR
  2668 00004712 E801DBFFFF          <1> 	CALL 	WAITF			; NEC FLAGS UPDATE CYCLE
  2669 00004717 9D                  <1> 	POPF				; RESTORE FLAGS FOR EXIT
  2670                              <1> 	;POP	BX			; RESTORE REG
  2671 00004718 C3                  <1> 	RETn				; CY = 0 FROM TEST INSTRUCTION
  2672                              <1> 
  2673                              <1> ;-------------------------------------------------------------------------------
  2674                              <1> ; SEEK
  2675                              <1> ;	THIS ROUTINE WILL MOVE THE HEAD ON THE NAMED DRIVE TO THE NAMED
  2676                              <1> ;	TRACK. IF THE DRIVE HAS NOT BEEN ACCESSED SINCE THE DRIVE
  2677                              <1> ;	RESET COMMAND WAS ISSUED, THE DRIVE WILL BE RECALIBRATED.
  2678                              <1> ;
  2679                              <1> ; ON ENTRY:	DI = DRIVE #
  2680                              <1> ;		CH = TRACK #
  2681                              <1> ;
  2682                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION.
  2683                              <1> ;		AX,BX,CX DX DESTROYED
  2684                              <1> ;-------------------------------------------------------------------------------
  2685                              <1> SEEK:
  2686 00004719 89FB                <1> 	MOV	eBX,eDI			; BX = DRIVE #
  2687 0000471B B001                <1> 	MOV	AL,1			; ESTABLISH MASK FOR RECALIBRATE TEST
  2688 0000471D 86CB                <1> 	XCHG	CL,BL			; SET DRIVE VALULE INTO CL
  2689 0000471F D2C0                <1> 	ROL	AL,CL			; SHIFT MASK BY THE DRIVE VALUE
  2690 00004721 86CB                <1> 	XCHG	CL,BL			; RECOVER TRACK VALUE
  2691 00004723 8405[055F0100]      <1> 	TEST	AL,[SEEK_STATUS]	; TEST FOR RECALIBRATE REQUIRED
  2692 00004729 7526                <1> 	JNZ	short J28A		; JUMP IF RECALIBRATE NOT REQUIRED
  2693                              <1> 
  2694 0000472B 0805[055F0100]      <1> 	OR	[SEEK_STATUS],AL	; TURN ON THE NO RECALIBRATE BIT IN FLAG
  2695 00004731 E862000000          <1> 	CALL	RECAL			; RECALIBRATE DRIVE
  2696 00004736 730E                <1> 	JNC	short AFT_RECAL		; RECALIBRATE DONE
  2697                              <1> 
  2698                              <1> ;-----	ISSUE RECALIBRATE FOR 80 TRACK DISKETTES
  2699                              <1> 
  2700 00004738 C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS],0	; CLEAR OUT INVALID STATUS
  2701 0000473F E854000000          <1> 	CALL	RECAL			; RECALIBRATE DRIVE
  2702 00004744 7251                <1> 	JC	short RB		; IF RECALIBRATE FAILS TWICE THEN ERROR
  2703                              <1> 
  2704                              <1> AFT_RECAL:
  2705 00004746 C687[195F0100]00    <1>         MOV     byte [DSK_TRK+eDI],0    ; SAVE NEW CYLINDER AS PRESENT POSITION
  2706 0000474D 08ED                <1> 	OR	CH,CH			; CHECK FOR SEEK TO TRACK 0
  2707 0000474F 743F                <1> 	JZ	short DO_WAIT		; HEAD SETTLE, CY = 0 IF JUMP
  2708                              <1> 
  2709                              <1> ;-----	DRIVE IS IN SYNCHRONIZATION WITH CONTROLLER, SEEK TO TRACK
  2710                              <1> 
  2711 00004751 F687[155F0100]20    <1> J28A:	TEST	byte [DSK_STATE+eDI],DBL_STEP ; CHECK FOR DOUBLE STEP REQUIRED
  2712 00004758 7402                <1> 	JZ	short _R7		; SINGLE STEP REQUIRED BYPASS DOUBLE
  2713 0000475A D0E5                <1> 	SHL	CH,1			; DOUBLE NUMBER OF STEP TO TAKE
  2714                              <1> 
  2715 0000475C 3AAF[195F0100]      <1> _R7:	CMP	CH, [DSK_TRK+eDI]	; SEE IF ALREADY AT THE DESIRED TRACK
  2716 00004762 7433                <1> 	JE	short RB		; IF YES, DO NOT NEED TO SEEK
  2717                              <1> 
  2718 00004764 BA[97470000]        <1> 	MOV	eDX, NEC_ERR		; LOAD RETURN ADDRESS
  2719 00004769 52                  <1> 	PUSH	eDX ; (*)		; ON STACK FOR NEC OUTPUT ERROR
  2720 0000476A 88AF[195F0100]      <1> 	MOV	[DSK_TRK+eDI],CH	; SAVE NEW CYLINDER AS PRESENT POSITION
  2721 00004770 B40F                <1> 	MOV	AH,0FH			; SEEK COMMAND TO NEC
  2722 00004772 E868FFFFFF          <1> 	CALL	NEC_OUTPUT
  2723 00004777 89FB                <1> 	MOV	eBX,eDI			; BX = DRIVE #
  2724 00004779 88DC                <1> 	MOV	AH,BL			; OUTPUT DRIVE NUMBER
  2725 0000477B E85FFFFFFF          <1> 	CALL	NEC_OUTPUT
  2726 00004780 8AA7[195F0100]      <1> 	MOV	AH, [DSK_TRK+eDI]	; GET CYLINDER NUMBER
  2727 00004786 E854FFFFFF          <1> 	CALL	NEC_OUTPUT
  2728 0000478B E829000000          <1> 	CALL	CHK_STAT_2		; ENDING INTERRUPT AND SENSE STATUS
  2729                              <1> 
  2730                              <1> ;-----	WAIT FOR HEAD SETTLE
  2731                              <1> 
  2732                              <1> DO_WAIT:
  2733 00004790 9C                  <1> 	PUSHF				; SAVE STATUS
  2734 00004791 E816FFFFFF          <1> 	CALL	HD_WAIT			; WAIT FOR HEAD SETTLE TIME
  2735 00004796 9D                  <1> 	POPF				; RESTORE STATUS
  2736                              <1> RB:
  2737                              <1> NEC_ERR:
  2738                              <1> 	; 08/02/2015 (code trick here from original IBM PC/AT DISKETTE.ASM)
  2739                              <1> 	; (*) nec_err -> retn (push edx -> pop edx) -> nec_err -> retn
  2740 00004797 C3                  <1> 	RETn				; RETURN TO CALLER
  2741                              <1> 
  2742                              <1> ;-------------------------------------------------------------------------------
  2743                              <1> ; RECAL
  2744                              <1> ;	RECALIBRATE DRIVE
  2745                              <1> ;
  2746                              <1> ; ON ENTRY:	DI = DRIVE #
  2747                              <1> ;
  2748                              <1> ; ON EXIT:	CY REFLECTS STATUS OF OPERATION.
  2749                              <1> ;-------------------------------------------------------------------------------
  2750                              <1> RECAL:
  2751 00004798 6651                <1> 	PUSH	CX
  2752 0000479A B8[B6470000]        <1> 	MOV	eAX, RC_BACK		; LOAD NEC_OUTPUT ERROR
  2753 0000479F 50                  <1> 	PUSH	eAX
  2754 000047A0 B407                <1> 	MOV	AH,07H			; RECALIBRATE COMMAND
  2755 000047A2 E838FFFFFF          <1> 	CALL	NEC_OUTPUT
  2756 000047A7 89FB                <1> 	MOV	eBX,eDI			; BX = DRIVE #
  2757 000047A9 88DC                <1> 	MOV	AH,BL
  2758 000047AB E82FFFFFFF          <1> 	CALL	NEC_OUTPUT		; OUTPUT THE DRIVE NUMBER
  2759 000047B0 E804000000          <1> 	CALL	CHK_STAT_2		; GET THE INTERRUPT AND SENSE INT STATUS
  2760 000047B5 58                  <1> 	POP	eAX			; THROW AWAY ERROR
  2761                              <1> RC_BACK:
  2762 000047B6 6659                <1> 	POP	CX
  2763 000047B8 C3                  <1> 	RETn
  2764                              <1> 
  2765                              <1> ;-------------------------------------------------------------------------------
  2766                              <1> ; CHK_STAT_2
  2767                              <1> ;	THIS ROUTINE HANDLES THE INTERRUPT RECEIVED AFTER RECALIBRATE,
  2768                              <1> ;	OR SEEK TO THE ADAPTER. THE INTERRUPT IS WAITED FOR, THE
  2769                              <1> ;	INTERRUPT STATUS SENSED, AND THE RESULT RETURNED TO THE CALLER.
  2770                              <1> ;
  2771                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION.
  2772                              <1> ;-------------------------------------------------------------------------------
  2773                              <1> CHK_STAT_2:
  2774 000047B9 B8[E1470000]        <1>         MOV     eAX, CS_BACK            ; LOAD NEC_OUTPUT ERROR ADDRESS
  2775 000047BE 50                  <1> 	PUSH	eAX
  2776 000047BF E828000000          <1> 	CALL	WAIT_INT		; WAIT FOR THE INTERRUPT
  2777 000047C4 721A                <1> 	JC	short J34		; IF ERROR, RETURN IT
  2778 000047C6 B408                <1> 	MOV	AH,08H			; SENSE INTERRUPT STATUS COMMAND
  2779 000047C8 E812FFFFFF          <1> 	CALL	NEC_OUTPUT
  2780 000047CD E84A000000          <1> 	CALL	RESULTS			; READ IN THE RESULTS
  2781 000047D2 720C                <1> 	JC	short J34
  2782 000047D4 A0[095F0100]        <1> 	MOV	AL,[NEC_STATUS]		; GET THE FIRST STATUS BYTE
  2783 000047D9 2460                <1> 	AND	AL,01100000B		; ISOLATE THE BITS
  2784 000047DB 3C60                <1> 	CMP	AL,01100000B		; TEST FOR CORRECT VALUE
  2785 000047DD 7403                <1> 	JZ	short J35		; IF ERROR, GO MARK IT
  2786 000047DF F8                  <1> 	CLC				; GOOD RETURN
  2787                              <1> J34:
  2788 000047E0 58                  <1> 	POP	eAX			; THROW AWAY ERROR RETURN
  2789                              <1> CS_BACK:
  2790 000047E1 C3                  <1> 	RETn
  2791                              <1> J35:
  2792 000047E2 800D[085F0100]40    <1> 	OR	byte [DSKETTE_STATUS], BAD_SEEK
  2793 000047E9 F9                  <1> 	STC				; ERROR RETURN CODE
  2794 000047EA EBF4                <1> 	JMP	SHORT J34
  2795                              <1> 
  2796                              <1> ;-------------------------------------------------------------------------------
  2797                              <1> ; WAIT_INT
  2798                              <1> ;	THIS ROUTINE WAITS FOR AN INTERRUPT TO OCCUR A TIME OUT ROUTINE
  2799                              <1> ;	TAKES PLACE DURING THE WAIT, SO THAT AN ERROR MAY BE RETURNED
  2800                              <1> ;	IF THE DRIVE IS NOT READY.
  2801                              <1> ;
  2802                              <1> ; ON EXIT: 	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION.
  2803                              <1> ;-------------------------------------------------------------------------------
  2804                              <1> 
  2805                              <1> ; 17/12/2014
  2806                              <1> ; 2.5 seconds waiting !
  2807                              <1> ;(AWARD BIOS - 1999, WAIT_FDU_INT_LOW, WAIT_FDU_INT_HI)
  2808                              <1> ; amount of time to wait for completion interrupt from NEC.
  2809                              <1> 
  2810                              <1> 
  2811                              <1> WAIT_INT:
  2812 000047EC FB                  <1> 	STI				; TURN ON INTERRUPTS, JUST IN CASE
  2813 000047ED F8                  <1> 	CLC				; CLEAR TIMEOUT INDICATOR
  2814                              <1>        ;MOV	BL,10			; CLEAR THE COUNTERS
  2815                              <1>        ;XOR	CX,CX			; FOR 2 SECOND WAIT
  2816                              <1> 
  2817                              <1> 	; Modification from AWARD BIOS - 1999 (ATORGS.ASM, WAIT
  2818                              <1> 	;
  2819                              <1> 	;WAIT_FOR_MEM:	
  2820                              <1> 	;	Waits for a bit at a specified memory location pointed
  2821                              <1> 	;	to by ES:[DI] to become set.
  2822                              <1> 	;INPUT:
  2823                              <1> 	;	AH=Mask to test with.
  2824                              <1> 	;	ES:[DI] = memory location to watch.
  2825                              <1> 	;	BH:CX=Number of memory refresh periods to delay.
  2826                              <1> 	;	     (normally 30 microseconds per period.)
  2827                              <1> 
  2828                              <1> 	; waiting for (max.) 2.5 secs in 30 micro units.
  2829                              <1> ;	mov 	cx, WAIT_FDU_INT_LO		; 017798
  2830                              <1> ;;	mov 	bl, WAIT_FDU_INT_HI
  2831                              <1> ;	mov 	bl, WAIT_FDU_INT_HI + 1
  2832                              <1> 	; 27/02/2015
  2833 000047EE B986450100          <1> 	mov 	ecx, WAIT_FDU_INT_LH	; 83334 (2.5 seconds)		
  2834                              <1> WFMS_CHECK_MEM:
  2835 000047F3 F605[055F0100]80    <1> 	test	byte [SEEK_STATUS],INT_FLAG ; TEST FOR INTERRUPT OCCURRING
  2836 000047FA 7516                <1>         jnz     short J37
  2837                              <1> WFMS_HI:
  2838 000047FC E461                <1> 	IN	AL,PORT_B  ; 061h	; SYS1, wait for lo to hi
  2839 000047FE A810                <1> 	TEST	AL,010H			; transition on memory
  2840 00004800 75FA                <1> 	JNZ	SHORT WFMS_HI		; refresh.
  2841                              <1> WFMS_LO:
  2842 00004802 E461                <1> 	IN	AL,PORT_B		;SYS1
  2843 00004804 A810                <1> 	TEST	AL,010H
  2844 00004806 74FA                <1> 	JZ	SHORT WFMS_LO
  2845 00004808 E2E9                <1>         LOOP    WFMS_CHECK_MEM
  2846                              <1> ;WFMS_OUTER_LP:
  2847                              <1> ;;	or	bl, bl			; check outer counter
  2848                              <1> ;;	jz	short J36A		; WFMS_TIMEOUT
  2849                              <1> ;	dec	bl
  2850                              <1> ;	jz	short J36A	
  2851                              <1> ;	jmp	short WFMS_CHECK_MEM
  2852                              <1> 
  2853                              <1> 	;17/12/2014
  2854                              <1> 	;16/12/2014
  2855                              <1> ;        mov     byte [wait_count], 0    ; Reset (INT 08H) counter
  2856                              <1> ;J36:
  2857                              <1> ;	TEST	byte [SEEK_STATUS],INT_FLAG ; TEST FOR INTERRUPT OCCURRING
  2858                              <1> ;	JNZ	short J37
  2859                              <1> 	;16/12/2014
  2860                              <1> 	;LOOP	J36			; COUNT DOWN WHILE WAITING
  2861                              <1> 	;DEC	BL			; SECOND LEVEL COUNTER
  2862                              <1> 	;JNZ	short J36
  2863                              <1> ;       cmp     byte [wait_count], 46   ; (46/18.2 seconds)
  2864                              <1> ;	jb	short J36
  2865                              <1> 
  2866                              <1> ;WFMS_TIMEOUT:
  2867                              <1> ;J36A:
  2868 0000480A 800D[085F0100]80    <1> 	OR	byte [DSKETTE_STATUS], TIME_OUT ; NOTHING HAPPENED
  2869 00004811 F9                  <1> 	STC				; ERROR RETURN
  2870                              <1> J37:
  2871 00004812 9C                  <1> 	PUSHF				; SAVE CURRENT CARRY
  2872 00004813 8025[055F0100]7F    <1> 	AND	byte [SEEK_STATUS], ~INT_FLAG ; TURN OFF INTERRUPT FLAG
  2873 0000481A 9D                  <1> 	POPF				; RECOVER CARRY
  2874 0000481B C3                  <1> 	RETn				; GOOD RETURN CODE
  2875                              <1> 
  2876                              <1> ;-------------------------------------------------------------------------------
  2877                              <1> ; RESULTS
  2878                              <1> ;	THIS ROUTINE WILL READ ANYTHING THAT THE NEC CONTROLLER RETURNS 
  2879                              <1> ;	FOLLOWING AN INTERRUPT.
  2880                              <1> ;
  2881                              <1> ; ON EXIT:	@DSKETTE_STATUS, CY REFLECT STATUS OF OPERATION.
  2882                              <1> ;		AX,BX,CX,DX DESTROYED
  2883                              <1> ;-------------------------------------------------------------------------------
  2884                              <1> RESULTS:
  2885 0000481C 57                  <1> 	PUSH	eDI
  2886 0000481D BF[095F0100]        <1> 	MOV	eDI, NEC_STATUS		; POINTER TO DATA AREA
  2887 00004822 B307                <1> 	MOV	BL,7			; MAX STATUS BYTES
  2888 00004824 66BAF403            <1> 	MOV	DX,03F4H		; STATUS PORT
  2889                              <1> 
  2890                              <1> ;-----	WAIT FOR REQUEST FOR MASTER
  2891                              <1> 
  2892                              <1> _R10: 
  2893                              <1> 	; 16/12/2014
  2894                              <1> 	; wait for (max) 0.5 seconds
  2895                              <1> 	;MOV	BH,2			; HIGH ORDER COUNTER
  2896                              <1> 	;XOR	CX,CX			; COUNTER
  2897                              <1> 
  2898                              <1> 	;Time to wait while waiting for each byte of NEC results = .5
  2899                              <1> 	;seconds.  .5 seconds = 500,000 micros.  500,000/30 = 16,667.
  2900                              <1> 	; 27/02/2015
  2901 00004828 B91B410000          <1> 	mov 	ecx, WAIT_FDU_RESULTS_LH ; 16667  
  2902                              <1> 	;mov	cx, WAIT_FDU_RESULTS_LO  ; 16667
  2903                              <1> 	;mov	bh, WAIT_FDU_RESULTS_HI+1 ; 0+1
  2904                              <1> 
  2905                              <1> WFPSR_OUTER_LP:
  2906                              <1> 	;
  2907                              <1> WFPSR_CHECK_PORT:
  2908                              <1> J39:					; WAIT FOR MASTER
  2909 0000482D EC                  <1> 	IN	AL,DX			; GET STATUS
  2910 0000482E 24C0                <1> 	AND	AL,11000000B		; KEEP ONLY STATUS AND DIRECTION
  2911 00004830 3CC0                <1> 	CMP	AL,11000000B		; STATUS 1 AND DIRECTION 1 ?
  2912 00004832 7418                <1> 	JZ	short J42		; STATUS AND DIRECTION OK
  2913                              <1> WFPSR_HI:
  2914 00004834 E461                <1> 	IN	AL, PORT_B	;061h	; SYS1	; wait for hi to lo
  2915 00004836 A810                <1> 	TEST	AL,010H			; transition on memory
  2916 00004838 75FA                <1> 	JNZ	SHORT WFPSR_HI		; refresh.
  2917                              <1> WFPSR_LO:
  2918 0000483A E461                <1> 	IN	AL, PORT_B		; SYS1
  2919 0000483C A810                <1> 	TEST	AL,010H
  2920 0000483E 74FA                <1> 	JZ	SHORT WFPSR_LO
  2921 00004840 E2EB                <1>         LOOP    WFPSR_CHECK_PORT
  2922                              <1> 	;; 27/02/2015
  2923                              <1> 	;;dec	bh
  2924                              <1> 	;;jnz	short WFPSR_OUTER_LP
  2925                              <1> 	;jmp	short WFPSR_TIMEOUT	; fail
  2926                              <1> 
  2927                              <1> 	;;mov	byte [wait_count], 0
  2928                              <1> ;J39:					; WAIT FOR MASTER
  2929                              <1> ;	IN	AL,DX			; GET STATUS
  2930                              <1> ;	AND	AL,11000000B		; KEEP ONLY STATUS AND DIRECTION
  2931                              <1> ;	CMP	AL,11000000B		; STATUS 1 AND DIRECTION 1 ?
  2932                              <1> ;	JZ	short J42		; STATUS AND DIRECTION OK
  2933                              <1> 	;LOOP	J39			; LOOP TILL TIMEOUT
  2934                              <1> 	;DEC	BH			; DECREMENT HIGH ORDER COUNTER
  2935                              <1> 	;JNZ	short J39		; REPEAT TILL DELAY DONE
  2936                              <1> 	;
  2937                              <1> 	;;cmp	byte [wait_count], 10  ; (10/18.2 seconds)
  2938                              <1> 	;;jb	short J39	
  2939                              <1> 
  2940                              <1> ;WFPSR_TIMEOUT:
  2941 00004842 800D[085F0100]80    <1> 	OR	byte [DSKETTE_STATUS],TIME_OUT
  2942 00004849 F9                  <1> 	STC				; SET ERROR RETURN
  2943 0000484A EB29                <1> 	JMP	SHORT POPRES		; POP REGISTERS AND RETURN
  2944                              <1> 
  2945                              <1> ;-----	READ IN THE STATUS
  2946                              <1> 
  2947                              <1> J42:
  2948 0000484C EB00                <1> 	JMP	$+2			; I/O DELAY
  2949 0000484E 6642                <1> 	INC	DX			; POINT AT DATA PORT
  2950 00004850 EC                  <1> 	IN	AL,DX			; GET THE DATA
  2951                              <1> 	; 16/12/2014
  2952                              <1> 	NEWIODELAY
  2952 00004851 E6EB                <2>  out 0ebh,al
  2953 00004853 8807                <1>         MOV     [eDI],AL                ; STORE THE BYTE
  2954 00004855 47                  <1> 	INC	eDI			; INCREMENT THE POINTER
  2955                              <1> 	; 16/12/2014
  2956                              <1> ;	push	cx
  2957                              <1> ;	mov	cx, 30
  2958                              <1> ;wdw2:
  2959                              <1> ;	NEWIODELAY
  2960                              <1> ;	loop	wdw2
  2961                              <1> ;	pop	cx
  2962                              <1> 
  2963 00004856 B903000000          <1> 	MOV	eCX,3			; MINIMUM 24 MICROSECONDS FOR NEC
  2964 0000485B E8B8D9FFFF          <1> 	CALL	WAITF			; WAIT 30 TO 45 MICROSECONDS
  2965 00004860 664A                <1> 	DEC	DX			; POINT AT STATUS PORT
  2966 00004862 EC                  <1> 	IN	AL,DX			; GET STATUS
  2967                              <1> 	; 16/12/2014
  2968                              <1> 	NEWIODELAY
  2968 00004863 E6EB                <2>  out 0ebh,al
  2969                              <1> 	;
  2970 00004865 A810                <1> 	TEST	AL,00010000B		; TEST FOR NEC STILL BUSY
  2971 00004867 740C                <1> 	JZ	short POPRES		; RESULTS DONE ?
  2972                              <1> 
  2973 00004869 FECB                <1> 	DEC	BL			; DECREMENT THE STATUS COUNTER
  2974 0000486B 75BB                <1>         JNZ     short _R10              ; GO BACK FOR MORE
  2975 0000486D 800D[085F0100]20    <1> 	OR	byte [DSKETTE_STATUS],BAD_NEC ; TOO MANY STATUS BYTES
  2976 00004874 F9                  <1> 	STC				; SET ERROR FLAG
  2977                              <1> 
  2978                              <1> ;-----	RESULT OPERATION IS DONE
  2979                              <1> POPRES:
  2980 00004875 5F                  <1> 	POP	eDI
  2981 00004876 C3                  <1> 	RETn				; RETURN WITH CARRY SET
  2982                              <1> 
  2983                              <1> ;-------------------------------------------------------------------------------
  2984                              <1> ; READ_DSKCHNG
  2985                              <1> ;	READS THE STATE OF THE DISK CHANGE LINE.
  2986                              <1> ;
  2987                              <1> ; ON ENTRY:	DI = DRIVE #
  2988                              <1> ;
  2989                              <1> ; ON EXIT:	DI = DRIVE #
  2990                              <1> ;		ZF = 0 : DISK CHANGE LINE INACTIVE
  2991                              <1> ;		ZF = 1 : DISK CHANGE LINE ACTIVE
  2992                              <1> ;		AX,CX,DX DESTROYED
  2993                              <1> ;-------------------------------------------------------------------------------
  2994                              <1> READ_DSKCHNG:
  2995 00004877 E8A2FDFFFF          <1> 	CALL	MOTOR_ON		; TURN ON THE MOTOR IF OFF
  2996 0000487C 66BAF703            <1> 	MOV	DX,03F7H		; ADDRESS DIGITAL INPUT REGISTER
  2997 00004880 EC                  <1> 	IN	AL,DX			; INPUT DIGITAL INPUT REGISTER
  2998 00004881 A880                <1> 	TEST	AL,DSK_CHG		; CHECK FOR DISK CHANGE LINE ACTIVE
  2999 00004883 C3                  <1> 	RETn				; RETURN TO CALLER WITH ZERO FLAG SET
  3000                              <1> 
  3001                              <1> ;-------------------------------------------------------------------------------
  3002                              <1> ; DRIVE_DET
  3003                              <1> ;	DETERMINES WHETHER DRIVE IS 80 OR 40 TRACKS AND
  3004                              <1> ;	UPDATES STATE INFORMATION ACCORDINGLY.
  3005                              <1> ; ON ENTRY:	DI = DRIVE #
  3006                              <1> ;-------------------------------------------------------------------------------
  3007                              <1> DRIVE_DET:
  3008 00004884 E895FDFFFF          <1> 	CALL	MOTOR_ON		; TURN ON MOTOR IF NOT ALREADY ON
  3009 00004889 E80AFFFFFF          <1> 	CALL	RECAL			; RECALIBRATE DRIVE
  3010 0000488E 7251                <1> 	JC	short DD_BAC		; ASSUME NO DRIVE PRESENT
  3011 00004890 B530                <1> 	MOV	CH,TRK_SLAP		; SEEK TO TRACK 48
  3012 00004892 E882FEFFFF          <1> 	CALL	SEEK
  3013 00004897 7248                <1> 	JC	short DD_BAC		; ERROR NO DRIVE
  3014 00004899 B50B                <1> 	MOV	CH,QUIET_SEEK+1		; SEEK TO TRACK 10
  3015                              <1> SK_GIN:
  3016 0000489B FECD                <1> 	DEC	CH			; DECREMENT TO NEXT TRACK
  3017 0000489D 6651                <1> 	PUSH	CX			; SAVE TRACK
  3018 0000489F E875FEFFFF          <1> 	CALL	SEEK
  3019 000048A4 723C                <1> 	JC	short POP_BAC		; POP AND RETURN
  3020 000048A6 B8[E2480000]        <1> 	MOV	eAX, POP_BAC		; LOAD NEC OUTPUT ERROR ADDRESS
  3021 000048AB 50                  <1> 	PUSH	eAX
  3022 000048AC B404                <1> 	MOV	AH,SENSE_DRV_ST		; SENSE DRIVE STATUS COMMAND BYTE
  3023 000048AE E82CFEFFFF          <1> 	CALL	NEC_OUTPUT		; OUTPUT TO NEC
  3024 000048B3 6689F8              <1> 	MOV	AX,DI			; AL = DRIVE
  3025 000048B6 88C4                <1> 	MOV	AH,AL			; AH = DRIVE
  3026 000048B8 E822FEFFFF          <1> 	CALL	NEC_OUTPUT		; OUTPUT TO NEC
  3027 000048BD E85AFFFFFF          <1> 	CALL	RESULTS			; GO GET STATUS
  3028 000048C2 58                  <1> 	POP	eAX			; THROW AWAY ERROR ADDRESS
  3029 000048C3 6659                <1> 	POP	CX			; RESTORE TRACK
  3030 000048C5 F605[095F0100]10    <1> 	TEST	byte [NEC_STATUS], HOME	; TRACK 0 ?
  3031 000048CC 74CD                <1> 	JZ	short SK_GIN		; GO TILL TRACK 0
  3032 000048CE 08ED                <1> 	OR	CH,CH			; IS HOME AT TRACK 0
  3033 000048D0 7408                <1> 	JZ	short IS_80		; MUST BE 80 TRACK DRIVE
  3034                              <1> 
  3035                              <1> ;	DRIVE IS A 360; SET DRIVE TO DETERMINED;
  3036                              <1> ;	SET MEDIA TO DETERMINED AT RATE 250.
  3037                              <1> 
  3038 000048D2 808F[155F0100]94    <1> 	OR	byte [DSK_STATE+eDI], DRV_DET+MED_DET+RATE_250
  3039 000048D9 C3                  <1> 	RETn				; ALL INFORMATION SET
  3040                              <1> IS_80:
  3041 000048DA 808F[155F0100]01    <1> 	OR	byte [DSK_STATE+eDI], TRK_CAPA ; SETUP 80 TRACK CAPABILITY
  3042                              <1> DD_BAC:
  3043 000048E1 C3                  <1> 	RETn
  3044                              <1> POP_BAC:
  3045 000048E2 6659                <1> 	POP	CX			; THROW AWAY
  3046 000048E4 C3                  <1> 	RETn
  3047                              <1> 
  3048                              <1> fdc_int:  
  3049                              <1> 	  ; 30/07/2015	
  3050                              <1> 	  ; 16/02/2015
  3051                              <1> ;int_0Eh: ; 11/12/2014
  3052                              <1> 
  3053                              <1> ;--- HARDWARE INT 0EH -- ( IRQ LEVEL  6 ) --------------------------------------
  3054                              <1> ; DISK_INT
  3055                              <1> ;	THIS ROUTINE HANDLES THE DISKETTE INTERRUPT.
  3056                              <1> ;
  3057                              <1> ; ON EXIT:	THE INTERRUPT FLAG IS SET IN @SEEK_STATUS.
  3058                              <1> ;-------------------------------------------------------------------------------
  3059                              <1> DISK_INT_1:
  3060                              <1> 
  3061 000048E5 6650                <1> 	PUSH	AX			; SAVE WORK REGISTER
  3062 000048E7 1E                  <1> 	push	ds
  3063 000048E8 66B81000            <1> 	mov	ax, KDATA
  3064 000048EC 8ED8                <1> 	mov 	ds, ax
  3065 000048EE 800D[055F0100]80    <1>         OR      byte [SEEK_STATUS], INT_FLAG ; TURN ON INTERRUPT OCCURRED
  3066 000048F5 B020                <1> 	MOV     AL,EOI                  ; END OF INTERRUPT MARKER
  3067 000048F7 E620                <1> 	OUT	INTA00,AL		; INTERRUPT CONTROL PORT
  3068 000048F9 1F                  <1> 	pop	ds
  3069 000048FA 6658                <1> 	POP	AX			; RECOVER REGISTER
  3070 000048FC CF                  <1> 	IRETd				; RETURN FROM INTERRUPT
  3071                              <1> 
  3072                              <1> ;-------------------------------------------------------------------------------
  3073                              <1> ; DSKETTE_SETUP
  3074                              <1> ;	THIS ROUTINE DOES A PRELIMINARY CHECK TO SEE WHAT TYPE OF
  3075                              <1> ;	DISKETTE DRIVES ARE ATTACH TO THE SYSTEM.
  3076                              <1> ;-------------------------------------------------------------------------------
  3077                              <1> 
  3078                              <1> ; 29/05/2016 - TRDOS 386 (TRDOS v2.0)
  3079                              <1> 
  3080                              <1> DSKETTE_SETUP:
  3081                              <1> 	;PUSH	AX			; SAVE REGISTERS
  3082                              <1> 	;PUSH	BX
  3083                              <1> 	;PUSH	CX
  3084 000048FD 52                  <1> 	PUSH	eDX
  3085                              <1> 	;PUSH	DI
  3086                              <1> 	;;PUSH	DS
  3087                              <1> 	; 14/12/2014
  3088                              <1> 	;mov	word [DISK_POINTER], MD_TBL6
  3089                              <1> 	;mov	[DISK_POINTER+2], cs
  3090                              <1> 	;
  3091                              <1> 	;OR	byte [RTC_WAIT_FLAG], 1	; NO RTC WAIT, FORCE USE OF LOOP
  3092 000048FE 31FF                <1> 	XOR	eDI,eDI			; INITIALIZE DRIVE POINTER
  3093 00004900 66C705[155F0100]00- <1> 	MOV	WORD [DSK_STATE],0	; INITIALIZE STATES
  3093 00004908 00                  <1>
  3094 00004909 8025[105F0100]33    <1> 	AND	byte [LASTRATE],~(STRT_MSK+SEND_MSK) ; CLEAR START & SEND
  3095 00004910 800D[105F0100]C0    <1> 	OR	byte [LASTRATE],SEND_MSK ; INITIALIZE SENT TO IMPOSSIBLE
  3096 00004917 C605[055F0100]00    <1> 	MOV	byte [SEEK_STATUS],0	; INDICATE RECALIBRATE NEEDED
  3097 0000491E C605[075F0100]00    <1> 	MOV	byte [MOTOR_COUNT],0	; INITIALIZE MOTOR COUNT
  3098 00004925 C605[065F0100]00    <1> 	MOV	byte [MOTOR_STATUS],0	; INITIALIZE DRIVES TO OFF STATE
  3099 0000492C C605[085F0100]00    <1> 	MOV	byte [DSKETTE_STATUS],0	; NO ERRORS
  3100                              <1> 	;
  3101                              <1> 	; 28/02/2015
  3102                              <1> 	;mov	word [cfd], 100h 
  3103 00004933 E82BF2FFFF          <1> 	call	DSK_RESET
  3104 00004938 5A                  <1> 	pop	edx
  3105 00004939 F8                  <1> 	clc	; 29/05/2016
  3106 0000493A C3                  <1> 	retn
  3107                              <1> 
  3108                              <1> ;SUP0:
  3109                              <1> ;	CALL	DRIVE_DET		; DETERMINE DRIVE
  3110                              <1> ;	CALL	XLAT_OLD		; TRANSLATE STATE TO COMPATIBLE MODE
  3111                              <1> ;	; 02/01/2015
  3112                              <1> ;	;INC	DI			; POINT TO NEXT DRIVE
  3113                              <1> ;	;CMP	DI,MAX_DRV		; SEE IF DONE
  3114                              <1> ;	;JNZ	short SUP0		; REPEAT FOR EACH ORIVE
  3115                              <1> ;       cmp     byte [fd1_type], 0	
  3116                              <1> ;	jna	short sup1
  3117                              <1> ;	or	di, di
  3118                              <1> ;	jnz	short sup1
  3119                              <1> ;	inc	di
  3120                              <1> ;       jmp     short SUP0
  3121                              <1> ;sup1:
  3122                              <1> ;	MOV	byte [SEEK_STATUS],0	; FORCE RECALIBRATE
  3123                              <1> ;	;AND	byte [RTC_WAIT_FLAG],0FEH ; ALLOW FOR RTC WAIT
  3124                              <1> ;	CALL	SETUP_END		; VARIOUS CLEANUPS
  3125                              <1> ;	;;POP	DS			; RESTORE CALLERS REGISTERS
  3126                              <1> ;	;POP	DI
  3127                              <1> ;	POP	eDX
  3128                              <1> ;	;POP	CX
  3129                              <1> ;	;POP	BX
  3130                              <1> ;	;POP	AX
  3131                              <1> ;	RETn
  3132                              <1> 
  3133                              <1> ;//////////////////////////////////////////////////////
  3134                              <1> ;; END OF DISKETTE I/O ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  3135                              <1> ;
  3136                              <1> 
  3137                              <1> int13h: ; 21/02/2015
  3138 0000493B F8                  <1> 	clc ; 20/07/2020
  3139 0000493C 9C                  <1> 	pushfd
  3140 0000493D 0E                  <1> 	push 	cs
  3141 0000493E E848010000          <1> 	call 	DISK_IO
  3142 00004943 C3                  <1> 	retn
  3143                              <1> 
  3144                              <1> ;;;;;; DISK I/O ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; 21/02/2015 ;;;
  3145                              <1> ;/////////////////////////////////////////////////////////////////////
  3146                              <1> 
  3147                              <1> ; DISK I/O - Erdogan Tan (Retro UNIX 386 v1 project)
  3148                              <1> ; 18/02/2016
  3149                              <1> ; 17/02/2016
  3150                              <1> ; 23/02/2015
  3151                              <1> ; 21/02/2015 (unix386.s)
  3152                              <1> ; 22/12/2014 - 14/02/2015 (dsectrm2.s)
  3153                              <1> ;
  3154                              <1> ; Original Source Code:
  3155                              <1> ; DISK ----- 09/25/85 FIXED DISK BIOS
  3156                              <1> ; (IBM PC XT Model 286 System BIOS Source Code, 04-21-86)
  3157                              <1> ;
  3158                              <1> ; Modifications: by reference of AWARD BIOS 1999 (D1A0622) 
  3159                              <1> ;		 Source Code - ATORGS.ASM, AHDSK.ASM
  3160                              <1> ;
  3161                              <1> 
  3162                              <1> 
  3163                              <1> ;The wait for controller to be not busy is 10 seconds.
  3164                              <1> ;10,000,000 / 30 = 333,333.  333,333 decimal = 051615h
  3165                              <1> ;;WAIT_HDU_CTLR_BUSY_LO	equ	1615h		
  3166                              <1> ;;WAIT_HDU_CTLR_BUSY_HI	equ	  05h
  3167                              <1> WAIT_HDU_CTRL_BUSY_LH	equ	51615h	 ;21/02/2015		
  3168                              <1> 
  3169                              <1> ;The wait for controller to issue completion interrupt is 10 seconds.
  3170                              <1> ;10,000,000 / 30 = 333,333.  333,333 decimal = 051615h
  3171                              <1> ;;WAIT_HDU_INT_LO	equ	1615h
  3172                              <1> ;;WAIT_HDU_INT_HI	equ	  05h
  3173                              <1> WAIT_HDU_INT_LH		equ	51615h	; 21/02/2015
  3174                              <1> 
  3175                              <1> ;The wait for Data request on read and write longs is
  3176                              <1> ;2000 us. (?)
  3177                              <1> ;;WAIT_HDU_DRQ_LO	equ	1000	; 03E8h
  3178                              <1> ;;WAIT_HDU_DRQ_HI	equ	0
  3179                              <1> WAIT_HDU_DRQ_LH		equ	1000	; 21/02/2015
  3180                              <1> 
  3181                              <1> ; Port 61h (PORT_B)
  3182                              <1> SYS1		equ	61h	; PORT_B  (diskette.inc)
  3183                              <1> 
  3184                              <1> ; 23/12/2014
  3185                              <1> %define CMD_BLOCK       eBP-8  ; 21/02/2015
  3186                              <1> 
  3187                              <1> ; 30/08/2020 - TRDOS 386 v2
  3188                              <1> 
  3189                              <1> ;--- INT 13H -------------------------------------------------------------------
  3190                              <1> ;									       :
  3191                              <1> ; FIXED DISK I/O INTERFACE						       :
  3192                              <1> ;									       :
  3193                              <1> ;	THIS INTERFACE PROVIDES ACCESS TO 5 1/4" FIXED DISKS THROUGH           :
  3194                              <1> ;	THE IBM FIXED DISK CONTROLLER.					       :
  3195                              <1> ;									       :
  3196                              <1> ;	THE  BIOS  ROUTINES  ARE  MEANT  TO  BE  ACCESSED  THROUGH	       :
  3197                              <1> ;	SOFTWARE  INTERRUPTS  ONLY.    ANY  ADDRESSES  PRESENT	IN	       :
  3198                              <1> ;	THESE  LISTINGS  ARE  INCLUDED	 ONLY	FOR  COMPLETENESS,	       :
  3199                              <1> ;	NOT  FOR  REFERENCE.  APPLICATIONS   WHICH  REFERENCE  ANY	       :
  3200                              <1> ;	ABSOLUTE  ADDRESSES  WITHIN  THE  CODE	SEGMENTS  OF  BIOS	       :
  3201                              <1> ;	VIOLATE  THE  STRUCTURE  AND  DESIGN  OF  BIOS. 		       :
  3202                              <1> ;									       :
  3203                              <1> ;------------------------------------------------------------------------------:
  3204                              <1> ;									       :
  3205                              <1> ; INPUT  (AH)= HEX COMMAND VALUE					       :
  3206                              <1> ;									       :
  3207                              <1> ;	(AH)= 00H  RESET DISK (DL = 80H,81H) / DISKETTE 		       :
  3208                              <1> ;	(AH)= 01H  READ THE STATUS OF THE LAST DISK OPERATION INTO (AL)        :
  3209                              <1> ;		    NOTE: DL < 80H - DISKETTE				       :
  3210                              <1> ;			  DL > 80H - DISK				       :
  3211                              <1> ;	(AH)= 02H  READ THE DESIRED SECTORS INTO MEMORY 		       :
  3212                              <1> ;	(AH)= 03H  WRITE THE DESIRED SECTORS FROM MEMORY		       :
  3213                              <1> ;	(AH)= 04H  VERIFY THE DESIRED SECTORS				       :
  3214                              <1> ;	(AH)= 05H  FORMAT THE DESIRED TRACK				       :
  3215                              <1> ;	(AH)= 06H  UNUSED						       :
  3216                              <1> ;	(AH)= 07H  UNUSED						       :
  3217                              <1> ;	(AH)= 08H  RETURN THE CURRENT DRIVE PARAMETERS			       :
  3218                              <1> ;	(AH)= 09H  INITIALIZE DRIVE PAIR CHARACTERISTICS		       :
  3219                              <1> ;		    INTERRUPT 41 POINTS TO DATA BLOCK FOR DRIVE 0	       :
  3220                              <1> ;		    INTERRUPT 46 POINTS TO DATA BLOCK FOR DRIVE 1	       :
  3221                              <1> ;	(AH)= 0AH  READ LONG						       :
  3222                              <1> ;	(AH)= 0BH  WRITE LONG  (READ & WRITE LONG ENCOMPASS 512 + 4 BYTES ECC) :
  3223                              <1> ;	(AH)= 0CH  SEEK 						       :
  3224                              <1> ;	(AH)= 0DH  ALTERNATE DISK RESET (SEE DL)			       :
  3225                              <1> ;	(AH)= 0EH  UNUSED						       :
  3226                              <1> ;	(AH)= 0FH  UNUSED						       :
  3227                              <1> ;	(AH)= 10H  TEST DRIVE READY					       :
  3228                              <1> ;	(AH)= 11H  RECALIBRATE						       :
  3229                              <1> ;	(AH)= 12H  UNUSED						       :
  3230                              <1> ;	(AH)= 13H  UNUSED						       :
  3231                              <1> ;	(AH)= 14H  CONTROLLER INTERNAL DIAGNOSTIC			       :
  3232                              <1> ;	(AH)= 15H  READ DASD TYPE					       :
  3233                              <1> ;									       :
  3234                              <1> ;-------------------------------------------------------------------------------
  3235                              <1> ;									       :
  3236                              <1> ;	REGISTERS USED FOR FIXED DISK OPERATIONS			       :
  3237                              <1> ;									       :
  3238                              <1> ;		(DL)	-  DRIVE NUMBER     (80H-81H FOR DISK. VALUE CHECKED)  :
  3239                              <1> ;		(DH)	-  HEAD NUMBER	    (0-15 ALLOWED, NOT VALUE CHECKED)  :
  3240                              <1> ;		(CH)	-  CYLINDER NUMBER  (0-1023, NOT VALUE CHECKED)(SEE CL):
  3241                              <1> ;		(CL)	-  SECTOR NUMBER    (1-17, NOT VALUE CHECKED)	       :
  3242                              <1> ;									       :
  3243                              <1> ;			   NOTE: HIGH 2 BITS OF CYLINDER NUMBER ARE PLACED     :
  3244                              <1> ;				 IN THE HIGH 2 BITS OF THE CL REGISTER	       :
  3245                              <1> ;				 (10 BITS TOTAL)			       :
  3246                              <1> ;									       :
  3247                              <1> ;		(AL)	-  NUMBER OF SECTORS (MAXIMUM POSSIBLE RANGE 1-80H,    :
  3248                              <1> ;					      FOR READ/WRITE LONG 1-79H)       :
  3249                              <1> ;									       :
  3250                              <1> ;		(ES:BX) -  ADDRESS OF BUFFER FOR READS AND WRITES,	       :
  3251                              <1> ;			   (NOT REQUIRED FOR VERIFY)			       :
  3252                              <1> ;									       :
  3253                              <1> ;		FORMAT (AH=5) ES:BX POINTS TO A 512 BYTE BUFFER. THE FIRST     :
  3254                              <1> ;			   2*(SECTORS/TRACK) BYTES CONTAIN F,N FOR EACH SECTOR.:
  3255                              <1> ;			   F = 00H FOR A GOOD SECTOR			       :
  3256                              <1> ;			       80H FOR A BAD SECTOR			       :
  3257                              <1> ;			   N = SECTOR NUMBER				       :
  3258                              <1> ;			   FOR AN INTERLEAVE OF 2 AND 17 SECTORS/TRACK	       :
  3259                              <1> ;			   THE TABLE SHOULD BE: 			       :
  3260                              <1> ;									       :
  3261                              <1> ;		   DB	   00H,01H,00H,0AH,00H,02H,00H,0BH,00H,03H,00H,0CH     :
  3262                              <1> ;		   DB	   00H,04H,00H,0DH,00H,05H,00H,0EH,00H,06H,00H,0FH     :
  3263                              <1> ;		   DB	   00H,07H,00H,10H,00H,08H,00H,11H,00H,09H	       :
  3264                              <1> ;									       :
  3265                              <1> ;-------------------------------------------------------------------------------
  3266                              <1> 
  3267                              <1> ;-------------------------------------------------------------------------------
  3268                              <1> ; OUTPUT								       :
  3269                              <1> ;	AH = STATUS OF CURRENT OPERATION				       :
  3270                              <1> ;	     STATUS BITS ARE DEFINED IN THE EQUATES BELOW		       :
  3271                              <1> ;	CY = 0	SUCCESSFUL OPERATION (AH=0 ON RETURN)			       :
  3272                              <1> ;	CY = 1	FAILED OPERATION (AH HAS ERROR REASON)			       :
  3273                              <1> ;									       :
  3274                              <1> ;	NOTE:	ERROR 11H  INDICATES THAT THE DATA READ HAD A RECOVERABLE      :
  3275                              <1> ;		ERROR WHICH WAS CORRECTED BY THE ECC ALGORITHM.  THE DATA      :
  3276                              <1> ;		IS PROBABLY GOOD,   HOWEVER THE BIOS ROUTINE INDICATES AN      :
  3277                              <1> ;		ERROR TO ALLOW THE CONTROLLING PROGRAM A CHANCE TO DECIDE      :
  3278                              <1> ;		FOR ITSELF.  THE  ERROR  MAY  NOT  RECUR  IF  THE DATA IS      :
  3279                              <1> ;		REWRITTEN.						       :
  3280                              <1> ;									       :
  3281                              <1> ;	IF DRIVE PARAMETERS WERE REQUESTED (DL >= 80H), 		       :
  3282                              <1> ;	   INPUT:							       :
  3283                              <1> ;	     (DL) = DRIVE NUMBER					       :	
  3284                              <1> ;	     ; 27/05/2016 - TRDOS 386 (TRDOS v2.0)						       :	 	
  3285                              <1> ;	     EBX = Buffer address for fixed disk parameters table (32 bytes)   :
  3286                              <1> ;	   OUTPUT:							       :
  3287                              <1> ;	     (DL) = NUMBER OF CONSECUTIVE ACKNOWLEDGING DRIVES ATTACHED (1-2)  :
  3288                              <1> ;		    (CONTROLLER CARD ZERO TALLY ONLY)			       :
  3289                              <1> ;	     (DH) = MAXIMUM USEABLE VALUE FOR HEAD NUMBER		       :
  3290                              <1> ;	     (CH) = MAXIMUM USEABLE VALUE FOR CYLINDER NUMBER		       :
  3291                              <1> ;	     (CL) = MAXIMUM USEABLE VALUE FOR SECTOR NUMBER		       :
  3292                              <1> ;		    AND CYLINDER NUMBER HIGH BITS			       :
  3293                              <1> ;									       :
  3294                              <1> ;	IF READ DASD TYPE WAS REQUESTED,				       :
  3295                              <1> ;									       :
  3296                              <1> ;	AH = 0 - NOT PRESENT						       :
  3297                              <1> ;	     1 - DISKETTE - NO CHANGE LINE AVAILABLE			       :
  3298                              <1> ;	     2 - DISKETTE - CHANGE LINE AVAILABLE			       :
  3299                              <1> ;	     3 - FIXED DISK						       :
  3300                              <1> ;									       :
  3301                              <1> ;	CX,DX = NUMBER OF 512 BYTE BLOCKS WHEN AH = 3			       :
  3302                              <1> ;									       :
  3303                              <1> ;	REGISTERS WILL BE PRESERVED EXCEPT WHEN THEY ARE USED TO RETURN        :
  3304                              <1> ;	INFORMATION.							       :
  3305                              <1> ;									       :
  3306                              <1> ;	NOTE: IF AN ERROR IS REPORTED BY THE DISK CODE, THE APPROPRIATE        :
  3307                              <1> ;		ACTION IS TO RESET THE DISK, THEN RETRY THE OPERATION.	       :
  3308                              <1> ;									       :
  3309                              <1> ;-------------------------------------------------------------------------------
  3310                              <1> 
  3311                              <1> SENSE_FAIL	EQU	0FFH		; NOT IMPLEMENTED
  3312                              <1> NO_ERR		EQU	0E0H		; STATUS ERROR/ERROR REGISTER=0
  3313                              <1> WRITE_FAULT	EQU	0CCH		; WRITE FAULT ON SELECTED DRIVE
  3314                              <1> UNDEF_ERR	EQU	0BBH		; UNDEFINED ERROR OCCURRED
  3315                              <1> NOT_RDY 	EQU	0AAH		; DRIVE NOT READY
  3316                              <1> TIME_OUT	EQU	80H		; ATTACHMENT FAILED TO RESPOND
  3317                              <1> BAD_SEEK	EQU	40H		; SEEK OPERATION FAILED
  3318                              <1> BAD_CNTLR	EQU	20H		; CONTROLLER HAS FAILED
  3319                              <1> DATA_CORRECTED	EQU	11H		; ECC CORRECTED DATA ERROR
  3320                              <1> BAD_ECC 	EQU	10H		; BAD ECC ON DISK READ
  3321                              <1> BAD_TRACK	EQU	0BH		; NOT IMPLEMENTED
  3322                              <1> BAD_SECTOR	EQU	0AH		; BAD SECTOR FLAG DETECTED
  3323                              <1> ;DMA_BOUNDARY	EQU	09H		; DATA EXTENDS TOO FAR
  3324                              <1> INIT_FAIL	EQU	07H		; DRIVE PARAMETER ACTIVITY FAILED
  3325                              <1> BAD_RESET	EQU	05H		; RESET FAILED
  3326                              <1> ;RECORD_NOT_FND	EQU	04H		; REQUESTED SECTOR NOT FOUND
  3327                              <1> ;BAD_ADDR_MARK	EQU	02H		; ADDRESS MARK NOT FOUND
  3328                              <1> ;BAD_CMD 	EQU	01H		; BAD COMMAND PASSED TO DISK I/O
  3329                              <1> 
  3330                              <1> ;--------------------------------------------------------
  3331                              <1> ;							:
  3332                              <1> ; FIXED DISK PARAMETER TABLE				:
  3333                              <1> ;  -  THE TABLE IS COMPOSED OF A BLOCK DEFINED AS:	:
  3334                              <1> ;							:
  3335                              <1> ;  +0	(1 WORD) - MAXIMUM NUMBER OF CYLINDERS		:
  3336                              <1> ;  +2	(1 BYTE) - MAXIMUM NUMBER OF HEADS		:
  3337                              <1> ;  +3	(1 WORD) - NOT USED/SEE PC-XT			:
  3338                              <1> ;  +5	(1 WORD) - STARTING WRITE PRECOMPENSATION CYL	:
  3339                              <1> ;  +7	(1 BYTE) - MAXIMUM ECC DATA BURST LENGTH	:
  3340                              <1> ;  +8	(1 BYTE) - CONTROL BYTE 			:
  3341                              <1> ;		   BIT	  7 DISABLE RETRIES -OR-	:
  3342                              <1> ;		   BIT	  6 DISABLE RETRIES		:
  3343                              <1> ;		   BIT	  3 MORE THAN 8 HEADS		:
  3344                              <1> ;  +9	(3 BYTES)- NOT USED/SEE PC-XT			:
  3345                              <1> ; +12	(1 WORD) - LANDING ZONE 			:
  3346                              <1> ; +14	(1 BYTE) - NUMBER OF SECTORS/TRACK		:
  3347                              <1> ; +15	(1 BYTE) - RESERVED FOR FUTURE USE		:
  3348                              <1> ;							:
  3349                              <1> ;	 - TO DYNAMICALLY DEFINE A SET OF PARAMETERS	:
  3350                              <1> ;	   BUILD A TABLE FOR UP TO 15 TYPES AND PLACE	:
  3351                              <1> ;	   THE CORRESPONDING VECTOR INTO INTERRUPT 41	:
  3352                              <1> ;	   FOR DRIVE 0 AND INTERRUPT 46 FOR DRIVE 1.	:
  3353                              <1> ;							:
  3354                              <1> ;--------------------------------------------------------
  3355                              <1> 
  3356                              <1> ;--------------------------------------------------------
  3357                              <1> ;							:
  3358                              <1> ; HARDWARE SPECIFIC VALUES				:
  3359                              <1> ;							:
  3360                              <1> ;  -  CONTROLLER I/O PORT				:
  3361                              <1> ;							:
  3362                              <1> ;     > WHEN READ FROM: 				:
  3363                              <1> ;	HF_PORT+0 - READ DATA (FROM CONTROLLER TO CPU)	:
  3364                              <1> ;	HF_PORT+1 - GET ERROR REGISTER			:
  3365                              <1> ;	HF_PORT+2 - GET SECTOR COUNT			:
  3366                              <1> ;	HF_PORT+3 - GET SECTOR NUMBER			:
  3367                              <1> ;	HF_PORT+4 - GET CYLINDER LOW			:
  3368                              <1> ;	HF_PORT+5 - GET CYLINDER HIGH (2 BITS)		:
  3369                              <1> ;	HF_PORT+6 - GET SIZE/DRIVE/HEAD 		:
  3370                              <1> ;	HF_PORT+7 - GET STATUS REGISTER 		:
  3371                              <1> ;							:
  3372                              <1> ;     > WHEN WRITTEN TO:				:
  3373                              <1> ;	HF_PORT+0 - WRITE DATA (FROM CPU TO CONTROLLER) :
  3374                              <1> ;	HF_PORT+1 - SET PRECOMPENSATION CYLINDER	:
  3375                              <1> ;	HF_PORT+2 - SET SECTOR COUNT			:
  3376                              <1> ;	HF_PORT+3 - SET SECTOR NUMBER			:
  3377                              <1> ;	HF_PORT+4 - SET CYLINDER LOW			:
  3378                              <1> ;	HF_PORT+5 - SET CYLINDER HIGH (2 BITS)		:
  3379                              <1> ;	HF_PORT+6 - SET SIZE/DRIVE/HEAD 		:
  3380                              <1> ;	HF_PORT+7 - SET COMMAND REGISTER		:
  3381                              <1> ;							:
  3382                              <1> ;--------------------------------------------------------
  3383                              <1> 
  3384                              <1> ;HF_PORT 	EQU	01F0H	; DISK PORT
  3385                              <1> ;HF1_PORT	equ	0170h	
  3386                              <1> ;HF_REG_PORT	EQU	03F6H
  3387                              <1> ;HF1_REG_PORT	equ	0376h
  3388                              <1> 
  3389                              <1> HDC1_BASEPORT	equ	1F0h
  3390                              <1> HDC2_BASEPORT	equ	170h		
  3391                              <1> 
  3392                              <1> align 2
  3393                              <1> 
  3394                              <1> ;-----		STATUS REGISTER
  3395                              <1> 
  3396                              <1> ST_ERROR	EQU	00000001B	;
  3397                              <1> ST_INDEX	EQU	00000010B	;
  3398                              <1> ST_CORRCTD	EQU	00000100B	; ECC CORRECTION SUCCESSFUL
  3399                              <1> ST_DRQ		EQU	00001000B	;
  3400                              <1> ST_SEEK_COMPL	EQU	00010000B	; SEEK COMPLETE
  3401                              <1> ST_WRT_FLT	EQU	00100000B	; WRITE FAULT
  3402                              <1> ST_READY	EQU	01000000B	;
  3403                              <1> ST_BUSY 	EQU	10000000B	;
  3404                              <1> 
  3405                              <1> ;-----		ERROR REGISTER
  3406                              <1> 
  3407                              <1> ERR_DAM 	EQU	00000001B	; DATA ADDRESS MARK NOT FOUND
  3408                              <1> ERR_TRK_0	EQU	00000010B	; TRACK 0 NOT FOUND ON RECAL
  3409                              <1> ERR_ABORT	EQU	00000100B	; ABORTED COMMAND
  3410                              <1> ;		EQU	00001000B	; NOT USED
  3411                              <1> ERR_ID		EQU	00010000B	; ID NOT FOUND
  3412                              <1> ;		EQU	00100000B	; NOT USED
  3413                              <1> ERR_DATA_ECC	EQU	01000000B
  3414                              <1> ERR_BAD_BLOCK	EQU	10000000B
  3415                              <1> 
  3416                              <1> 
  3417                              <1> RECAL_CMD	EQU	00010000B	; DRIVE RECAL	(10H)
  3418                              <1> READ_CMD	EQU	00100000B	;	READ	(20H)
  3419                              <1> WRITE_CMD	EQU	00110000B	;	WRITE	(30H)
  3420                              <1> VERIFY_CMD	EQU	01000000B	;	VERIFY	(40H)
  3421                              <1> FMTTRK_CMD	EQU	01010000B	; FORMAT TRACK	(50H)
  3422                              <1> INIT_CMD	EQU	01100000B	;   INITIALIZE	(60H)
  3423                              <1> SEEK_CMD	EQU	01110000B	;	SEEK	(70H)
  3424                              <1> DIAG_CMD	EQU	10010000B	; DIAGNOSTIC	(90H)
  3425                              <1> SET_PARM_CMD	EQU	10010001B	; DRIVE PARMS	(91H)
  3426                              <1> NO_RETRIES	EQU	00000001B	; CHD MODIFIER	(01H)
  3427                              <1> ECC_MODE	EQU	00000010B	; CMD MODIFIER	(02H)
  3428                              <1> BUFFER_MODE	EQU	00001000B	; CMD MODIFIER	(08H)
  3429                              <1> 
  3430                              <1> ;MAX_FILE	EQU	2
  3431                              <1> ;S_MAX_FILE	EQU	2
  3432                              <1> MAX_FILE	equ	4		; 22/12/2014
  3433                              <1> S_MAX_FILE	equ	4		; 22/12/2014
  3434                              <1> 
  3435                              <1> DELAY_1 	EQU	25H		; DELAY FOR OPERATION COMPLETE
  3436                              <1> DELAY_2 	EQU	0600H		; DELAY FOR READY
  3437                              <1> DELAY_3 	EQU	0100H		; DELAY FOR DATA REQUEST
  3438                              <1> 
  3439                              <1> HF_FAIL 	EQU	08H		; CMOS FLAG IN BYTE 0EH
  3440                              <1> 
  3441                              <1> ;-----		COMMAND BLOCK REFERENCE
  3442                              <1> 
  3443                              <1> ;CMD_BLOCK      EQU     BP-8            ; @CMD_BLOCK REFERENCES BLOCK HEAD IN SS
  3444                              <1> 					;  (BP) POINTS TO COMMAND BLOCK TAIL
  3445                              <1> 					;	AS DEFINED BY THE "ENTER" PARMS
  3446                              <1> ; 19/12/2014
  3447                              <1> ORG_VECTOR	equ	4*13h		; INT 13h vector
  3448                              <1> DISK_VECTOR	equ	4*40h		; INT 40h vector (for floppy disks)
  3449                              <1> ;HDISK_INT	equ	4*76h		; Primary HDC - Hardware interrupt (IRQ14)
  3450                              <1> ;HDISK_INT1	equ	4*76h		; Primary HDC - Hardware interrupt (IRQ14)
  3451                              <1> ;HDISK_INT2	equ	4*77h		; Secondary HDC - Hardware interrupt (IRQ15)
  3452                              <1> ;HF_TBL_VEC	equ	4*41h		; Pointer to 1st fixed disk parameter table
  3453                              <1> ;HF1_TBL_VEC	equ	4*46h		; Pointer to 2nd fixed disk parameter table
  3454                              <1> 
  3455                              <1> align 2
  3456                              <1> 
  3457                              <1> ;----------------------------------------------------------------
  3458                              <1> ; FIXED DISK I/O SETUP						:
  3459                              <1> ;								:
  3460                              <1> ;  -  ESTABLISH TRANSFER VECTORS FOR THE FIXED DISK		:
  3461                              <1> ;  -  PERFORM POWER ON DIAGNOSTICS				:
  3462                              <1> ;     SHOULD AN ERROR OCCUR A "1701" MESSAGE IS DISPLAYED       :
  3463                              <1> ;								:
  3464                              <1> ;----------------------------------------------------------------
  3465                              <1> 
  3466                              <1> ; 29/05/2016 - TRDOS 386 (TRDOS v2.0)
  3467                              <1> 
  3468                              <1> DISK_SETUP:
  3469                              <1> 	;CLI
  3470                              <1> 	;;MOV	AX,ABS0 			; GET ABSOLUTE SEGMENT
  3471                              <1> 	;xor	ax,ax
  3472                              <1> 	;MOV	DS,AX				; SET SEGMENT REGISTER
  3473                              <1> 	;MOV	AX, [ORG_VECTOR] 		; GET DISKETTE VECTOR
  3474                              <1> 	;MOV	[DISK_VECTOR],AX		;  INTO INT 40H
  3475                              <1> 	;MOV	AX, [ORG_VECTOR+2]
  3476                              <1> 	;MOV	[DISK_VECTOR+2],AX
  3477                              <1> 	;MOV	word [ORG_VECTOR],DISK_IO	; FIXED DISK HANDLER
  3478                              <1> 	;MOV	[ORG_VECTOR+2],CS
  3479                              <1> 	; 1st controller (primary master, slave)   - IRQ 14
  3480                              <1> 	;;MOV	word [HDISK_INT],HD_INT		; FIXED DISK INTERRUPT
  3481                              <1> 	;mov	word [HDISK_INT1],HD_INT	;
  3482                              <1> 	;;MOV	[HDISK_INT+2],CS
  3483                              <1> 	;mov	[HDISK_INT1+2],CS
  3484                              <1> 	; 2nd controller (secondary master, slave) - IRQ 15
  3485                              <1> 	;mov	word [HDISK_INT2],HD1_INT	;
  3486                              <1> 	;mov	[HDISK_INT2+2],CS
  3487                              <1> 	;
  3488                              <1> 	;;MOV	word [HF_TBL_VEC],HD0_DPT	; PARM TABLE DRIVE 80
  3489                              <1> 	;;MOV	word [HF_TBL_VEC+2],DPT_SEGM
  3490                              <1> 	;;MOV	word [HF1_TBL_VEC],HD1_DPT	; PARM TABLE DRIVE 81
  3491                              <1> 	;;MOV	word [HF1_TBL_VEC+2],DPT_SEGM
  3492                              <1> 	;push	cs
  3493                              <1> 	;pop	ds
  3494                              <1> 	;mov	word [HDPM_TBL_VEC],HD0_DPT	; PARM TABLE DRIVE 80h
  3495                              <1> 	;mov	word [HDPM_TBL_VEC+2],DPT_SEGM
  3496 00004944 C705[205F0100]0000- <1> 	mov 	dword [HDPM_TBL_VEC], (DPT_SEGM*16)+HD0_DPT
  3496 0000494C 0900                <1>
  3497                              <1> 	;mov	word [HDPS_TBL_VEC],HD1_DPT	; PARM TABLE DRIVE 81h
  3498                              <1> 	;mov	word [HDPS_TBL_VEC+2],DPT_SEGM
  3499 0000494E C705[245F0100]2000- <1> 	mov 	dword [HDPS_TBL_VEC], (DPT_SEGM*16)+HD1_DPT
  3499 00004956 0900                <1>
  3500                              <1> 	;mov	word [HDSM_TBL_VEC],HD2_DPT	; PARM TABLE DRIVE 82h
  3501                              <1> 	;mov	word [HDSM_TBL_VEC+2],DPT_SEGM
  3502 00004958 C705[285F0100]4000- <1> 	mov 	dword [HDSM_TBL_VEC], (DPT_SEGM*16)+HD2_DPT
  3502 00004960 0900                <1>
  3503                              <1> 	;mov	word [HDSS_TBL_VEC],HD3_DPT	; PARM TABLE DRIVE 83h
  3504                              <1> 	;mov	word [HDSS_TBL_VEC+2],DPT_SEGM
  3505 00004962 C705[2C5F0100]6000- <1> 	mov 	dword [HDSS_TBL_VEC], (DPT_SEGM*16)+HD3_DPT
  3505 0000496A 0900                <1>
  3506                              <1> 	;
  3507                              <1> 	;;IN	AL,INTB01		; TURN ON SECOND INTERRUPT CHIP
  3508                              <1> 	;;;AND	AL,0BFH
  3509                              <1> 	;;and	al, 3Fh			; enable IRQ 14 and IRQ 15
  3510                              <1> 	;;;JMP	$+2
  3511                              <1> 	;;IODELAY
  3512                              <1> 	;;OUT	INTB01,AL
  3513                              <1> 	;;IODELAY
  3514                              <1> 	;;IN	AL,INTA01		; LET INTERRUPTS PASS THRU TO
  3515                              <1> 	;;AND	AL,0FBH 		;  SECOND CHIP
  3516                              <1> 	;;;JMP	$+2
  3517                              <1> 	;;IODELAY
  3518                              <1> 	;;OUT	INTA01,AL
  3519                              <1> 	;
  3520                              <1> 	;STI
  3521                              <1> 	;;PUSH	DS			; MOVE ABS0 POINTER TO
  3522                              <1> 	;;POP	ES			; EXTRA SEGMENT POINTER
  3523                              <1> 	;;;CALL	DDS			; ESTABLISH DATA SEGMENT
  3524                              <1> 	;;MOV	byte [DISK_STATUS1],0 	; RESET THE STATUS INDICATOR
  3525                              <1> 	;;MOV	byte [HF_NUM],0		; ZERO NUMBER OF FIXED DISKS
  3526                              <1> 	;;MOV	byte [CONTROL_BYTE],0
  3527                              <1> 	;;MOV	byte [PORT_OFF],0	; ZERO CARD OFFSET
  3528                              <1> 	; 20/12/2014 - private code by Erdogan Tan
  3529                              <1> 		      ; (out of original PC-AT, PC-XT BIOS code)
  3530                              <1> 	;mov	si, hd0_type
  3531 0000496C BE[B0640000]        <1> 	mov	esi, hd0_type
  3532                              <1> 	;mov	cx, 4
  3533 00004971 B904000000          <1> 	mov	ecx, 4
  3534                              <1> hde_l:
  3535 00004976 AC                  <1> 	lodsb
  3536 00004977 3C80                <1> 	cmp	al, 80h			; 8?h = existing
  3537 00004979 7206                <1> 	jb	short _L4
  3538 0000497B FE05[1C5F0100]      <1> 	inc	byte [HF_NUM]		; + 1 hard (fixed) disk drives
  3539                              <1> _L4: ; 26/02/2015
  3540 00004981 E2F3                <1> 	loop	hde_l	
  3541                              <1> ;_L4:					; 0 <= [HF_NUM] =< 4
  3542                              <1> ;L4:
  3543                              <1> 	; 
  3544                              <1> 	;; 31/12/2014 - cancel controller diagnostics here
  3545                              <1> 	;;;mov 	cx, 3  ; 26/12/2014 (Award BIOS 1999)
  3546                              <1> 	;;mov 	cl, 3
  3547                              <1> 	;;
  3548                              <1> 	;;MOV	DL,80H			; CHECK THE CONTROLLER
  3549                              <1> ;;hdc_dl:
  3550                              <1> 	;;MOV	AH,14H			; USE CONTROLLER DIAGNOSTIC COMMAND
  3551                              <1> 	;;INT	13H			; CALL BIOS WITH DIAGNOSTIC COMMAND
  3552                              <1> 	;;;JC	short CTL_ERRX		; DISPLAY ERROR MESSAGE IF BAD RETURN
  3553                              <1> 	;;;jc	short POD_DONE ;22/12/2014
  3554                              <1> 	;;jnc	short hdc_reset0
  3555                              <1> 	;;loop	hdc_dl
  3556                              <1> 	;;; 27/12/2014
  3557                              <1> 	;;stc
  3558                              <1> 	;;retn
  3559                              <1> 	;
  3560                              <1> ;;hdc_reset0:
  3561                              <1> 	; 18/01/2015
  3562 00004983 8A0D[1C5F0100]      <1> 	mov	cl, [HF_NUM]
  3563 00004989 20C9                <1> 	and	cl, cl
  3564 0000498B 740E                <1> 	jz	short POD_DONE
  3565                              <1> 	;
  3566 0000498D B27F                <1> 	mov	dl, 7Fh
  3567                              <1> hdc_reset1:
  3568 0000498F FEC2                <1> 	inc	dl
  3569                              <1> 	;; 31/12/2015
  3570                              <1> 	;;push	dx
  3571                              <1> 	;;push	cx
  3572                              <1> 	;;push	ds
  3573                              <1> 	;;sub	ax, ax
  3574                              <1> 	;;mov	ds, ax
  3575                              <1> 	;;MOV	AX, [TIMER_LOW]		; GET START TIMER COUNTS
  3576                              <1> 	;;pop	ds
  3577                              <1> 	;;MOV	BX,AX
  3578                              <1> 	;;ADD	AX,6*182		; 60 SECONDS* 18.2
  3579                              <1> 	;;MOV	CX,AX
  3580                              <1> 	;;mov	word [wait_count], 0	; 22/12/2014 (reset wait counter)
  3581                              <1> 	;;
  3582                              <1> 	;; 31/12/2014 - cancel HD_RESET_1
  3583                              <1> 	;;CALL	HD_RESET_1		; SET UP DRIVE 0, (1,2,3)
  3584                              <1> 	;;pop	cx
  3585                              <1> 	;;pop	dx
  3586                              <1> 	;;
  3587                              <1> 	; 18/01/2015
  3588 00004991 B40D                <1> 	mov	ah, 0Dh ; ALTERNATE RESET
  3589                              <1> 	;int	13h
  3590 00004993 E8A3FFFFFF          <1> 	call	int13h
  3591 00004998 E2F5                <1> 	loop	hdc_reset1
  3592 0000499A F8                  <1> 	clc 	; 29/05/2016
  3593                              <1> POD_DONE:
  3594 0000499B C3                  <1> 	RETn
  3595                              <1> 
  3596                              <1> ;;-----	POD_ERROR
  3597                              <1> 
  3598                              <1> ;;CTL_ERRX:
  3599                              <1> ;	;MOV	SI,OFFSET F1782 	; CONTROLLER ERROR
  3600                              <1> ;	;CALL	SET_FAIL		; DO NOT IPL FROM DISK
  3601                              <1> ;	;CALL	E_MSG			; DISPLAY ERROR AND SET (BP) ERROR FLAG
  3602                              <1> ;	;JMP	short POD_DONE
  3603                              <1> 
  3604                              <1> ;;HD_RESET_1:
  3605                              <1> ;;	;PUSH	BX			; SAVE TIMER LIMITS
  3606                              <1> ;;	;PUSH	CX
  3607                              <1> ;;RES_1: MOV	AH,09H			; SET DRIVE PARAMETERS
  3608                              <1> ;;	INT	13H
  3609                              <1> ;;	JC	short RES_2
  3610                              <1> ;;	MOV	AH,11H			; RECALIBRATE DRIVE
  3611                              <1> ;;	INT	13H
  3612                              <1> ;;	JNC	short RES_CK		; DRIVE OK
  3613                              <1> ;;RES_2: ;CALL	POD_TCHK		; CHECK TIME OUT
  3614                              <1> ;;	cmp	word [wait_count], 6*182 ; waiting time (in timer ticks)
  3615                              <1> ;;					; (30 seconds)		
  3616                              <1> ;;	;cmc
  3617                              <1> ;;	;JNC	short RES_1
  3618                              <1> ;;	jb	short RES_1
  3619                              <1> ;;;RES_FL: ;MOV	SI,OFFSET F1781 	; INDICATE DISK 1 FAILURE;
  3620                              <1> ;;	;TEST	DL,1
  3621                              <1> ;;	;JNZ	RES_E1
  3622                              <1> ;;	;MOV	SI,OFFSET F1780 	; INDICATE DISK 0 FAILURE
  3623                              <1> ;;	;CALL	SET_FAIL		; DO NOT TRY TO IPL DISK 0
  3624                              <1> ;;	;JMP	SHORT RES_E1
  3625                              <1> ;;RES_ER: ; 22/12/2014
  3626                              <1> ;;RES_OK:
  3627                              <1> ;;	;POP	CX			; RESTORE TIMER LIMITS
  3628                              <1> ;;	;POP	BX
  3629                              <1> ;;	RETn
  3630                              <1> ;;
  3631                              <1> ;;RES_RS: MOV	AH,00H			; RESET THE DRIVE
  3632                              <1> ;;	INT	13H
  3633                              <1> ;;RES_CK: MOV	AH,08H			; GET MAX CYLINDER,HEAD,SECTOR
  3634                              <1> ;;	MOV	BL,DL			; SAVE DRIVE CODE
  3635                              <1> ;;	INT	13H
  3636                              <1> ;;	JC	short RES_ER
  3637                              <1> ;;	MOV	[NEC_STATUS],CX 	; SAVE MAX CYLINDER, SECTOR
  3638                              <1> ;;	MOV	DL,BL			; RESTORE DRIVE CODE
  3639                              <1> ;;RES_3: MOV	AX,0401H		; VERIFY THE LAST SECTOR
  3640                              <1> ;;	INT	13H
  3641                              <1> ;;	JNC	short RES_OK		; VERIFY OK
  3642                              <1> ;;	CMP	AH,BAD_SECTOR		; OK ALSO IF JUST ID READ
  3643                              <1> ;;	JE	short RES_OK
  3644                              <1> ;;	CMP	AH,DATA_CORRECTED
  3645                              <1> ;;	JE	short RES_OK
  3646                              <1> ;;	CMP	AH,BAD_ECC
  3647                              <1> ;;	JE	short RES_OK
  3648                              <1> ;;	;CALL	POD_TCHK		; CHECK FOR TIME OUT
  3649                              <1> ;;	cmp	word [wait_count], 6*182 ; waiting time (in timer ticks)
  3650                              <1> ;;					; (60 seconds)		
  3651                              <1> ;;	cmc
  3652                              <1> ;;	JC	short RES_ER		; FAILED
  3653                              <1> ;;	MOV	CX,[NEC_STATUS] 	; GET SECTOR ADDRESS, AND CYLINDER
  3654                              <1> ;;	MOV	AL,CL			; SEPARATE OUT SECTOR NUMBER
  3655                              <1> ;;	AND	AL,3FH
  3656                              <1> ;;	DEC	AL			; TRY PREVIOUS ONE
  3657                              <1> ;;	JZ	short RES_RS		; WE'VE TRIED ALL SECTORS ON TRACK
  3658                              <1> ;;	AND	CL,0C0H 		; KEEP CYLINDER BITS
  3659                              <1> ;;	OR	CL,AL			; MERGE SECTOR WITH CYLINDER BITS
  3660                              <1> ;;	MOV	[NEC_STATUS],CX 	; SAVE CYLINDER, NEW SECTOR NUMBER
  3661                              <1> ;;	JMP	short RES_3		; TRY AGAIN
  3662                              <1> ;;;RES_ER: MOV	SI,OFFSET F1791 	; INDICATE DISK 1 ERROR
  3663                              <1> ;;	;TEST	DL,1
  3664                              <1> ;;	;JNZ	short RES_E1
  3665                              <1> ;;	;MOV	SI,OFFSET F1790 	; INDICATE DISK 0 ERROR
  3666                              <1> ;;;RES_E1:
  3667                              <1> ;;	;CALL	E_MSG			; DISPLAY ERROR AND SET (BP) ERROR FLAG
  3668                              <1> ;;;RES_OK:
  3669                              <1> ;;	;POP	CX			; RESTORE TIMER LIMITS
  3670                              <1> ;;	;POP	BX
  3671                              <1> ;;	;RETn
  3672                              <1> ;
  3673                              <1> ;;SET_FAIL:
  3674                              <1> ;	;MOV	AX,X*(CMOS_DIAG+NMI)	; GET CMOS ERROR BYTE
  3675                              <1> ;	;CALL	CMOS_READ
  3676                              <1> ;	;OR	AL,HF_FAIL		; SET DO NOT IPL FROM DISK FLAG
  3677                              <1> ;	;XCHG	AH,AL			; SAVE IT
  3678                              <1> ;	;CALL	CMOS_WRITE		; PUT IT OUT
  3679                              <1> ;	;RETn
  3680                              <1> ;
  3681                              <1> ;;POD_TCHK:				; CHECK FOR 30 SECOND TIME OUT
  3682                              <1> ;	;POP	AX			; SAVE RETURN
  3683                              <1> ;	;POP	CX			; GET TIME OUT LIMITS
  3684                              <1> ;	;POP	BX
  3685                              <1> ;	;PUSH	BX			; AND SAVE THEM AGAIN
  3686                              <1> ;	;PUSH	CX
  3687                              <1> ;	;PUSH	AX
  3688                              <1> ;	;push	ds
  3689                              <1> ;	;xor	ax, ax
  3690                              <1> ;	;mov	ds, ax			; RESTORE RETURN
  3691                              <1> ;	;MOV	AX, [TIMER_LOW]		; AX = CURRENT TIME
  3692                              <1> ;	;				; BX = START TIME
  3693                              <1> ;	;				; CX = END TIME
  3694                              <1> ;	;pop	ds
  3695                              <1> ;	;CMP	BX,CX
  3696                              <1> ;	;JB	short TCHK1		; START < END
  3697                              <1> ;	;CMP	BX,AX
  3698                              <1> ;	;JB	short TCHKG		; END < START < CURRENT
  3699                              <1> ;	;JMP	SHORT TCHK2		; END, CURRENT < START
  3700                              <1> ;;TCHK1: CMP	AX,BX
  3701                              <1> ;;	JB	short TCHKNG		; CURRENT < START < END
  3702                              <1> ;;TCHK2: CMP	AX,CX
  3703                              <1> ;;	JB	short TCHKG		; START < CURRENT < END
  3704                              <1> ;;					; OR CURRENT < END < START
  3705                              <1> ;;TCHKNG: STC				; CARRY SET INDICATES TIME OUT
  3706                              <1> ;;	RETn
  3707                              <1> ;;TCHKG: CLC				; INDICATE STILL TIME
  3708                              <1> ;;	RETn
  3709                              <1> ;;
  3710                              <1> ;;int_13h:
  3711                              <1> 
  3712                              <1> ;----------------------------------------
  3713                              <1> ;	FIXED DISK BIOS ENTRY POINT	:
  3714                              <1> ;----------------------------------------
  3715                              <1> 
  3716                              <1> ; 30/08/2020
  3717                              <1> ; 29/08/2020
  3718                              <1> ; 15/01/2017
  3719                              <1> ; 14/01/2017
  3720                              <1> ; 07/01/2017
  3721                              <1> ; 02/01/2017
  3722                              <1> ; 01/06/2016
  3723                              <1> ; 16/05/2016, 27/05/2016, 28/05/2016, 29/05/2016
  3724                              <1> ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  3725                              <1> int33h:  ; DISK I/O
  3726                              <1> 	; 29/05/2016
  3727 0000499C 80642408FE          <1> 	and	byte [esp+8], 11111110b  ; clear carry bit of eflags register
  3728                              <1> 	; 16/05/2016
  3729 000049A1 1E                  <1> 	push	ds
  3730 000049A2 53                  <1> 	push	ebx ; user's buffer address (virtual)
  3731 000049A3 66BB1000            <1> 	mov	bx, KDATA ; System (Kernel's) data segment
  3732 000049A7 8EDB                <1> 	mov	ds, bx
  3733                              <1> 
  3734                              <1> 	;;15/01/2017
  3735                              <1> 	; 14/01/2017
  3736                              <1> 	; 02/01/2017
  3737                              <1> 	;;mov	byte [intflg], 33h	; disk io interrupt 
  3738                              <1> 	;pop	ebx
  3739                              <1> 	;mov	[user_buffer], ebx		
  3740                              <1> 
  3741 000049A9 8F05[0C6B0100]      <1> 	pop	dword [user_buffer] ; 01/06/2016
  3742                              <1> 
  3743 000049AF C605[46640100]00    <1> 	mov	byte [scount], 0 ; sector count for transfer
  3744 000049B6 80FC03              <1> 	cmp	ah, 03h ; chs write
  3745 000049B9 7744                <1> 	ja	short int33h_2
  3746 000049BB 7407                <1> 	je	short int33h_0
  3747 000049BD 80FC02              <1> 	cmp	ah, 02h ; chs read
  3748 000049C0 726F                <1> 	jb	short int33h_5
  3749 000049C2 EB68                <1> 	jmp	short int33h_4
  3750                              <1> int33h_0:
  3751                              <1> 	; transfer user's buffer content to sector buffer
  3752 000049C4 51                  <1> 	push	ecx
  3753 000049C5 0FB6C8              <1> 	movzx	ecx, al
  3754                              <1> int33h_1:
  3755 000049C8 56                  <1> 	push	esi
  3756 000049C9 8B35[0C6B0100]      <1> 	mov	esi, [user_buffer]
  3757                              <1> 	; esi = user's buffer address (virtual, ebx)
  3758 000049CF 57                  <1> 	push	edi
  3759 000049D0 06                  <1> 	push	es
  3760 000049D1 50                  <1> 	push	eax
  3761 000049D2 66B81000            <1> 	mov	ax, KDATA
  3762 000049D6 8EC0                <1> 	mov	es, ax
  3763 000049D8 BF00000700          <1> 	mov	edi, Cluster_Buffer
  3764 000049DD C1E109              <1> 	shl	ecx, 9 ; * 512
  3765 000049E0 E8C7A30000          <1> 	call	transfer_from_user_buffer
  3766 000049E5 58                  <1> 	pop	eax
  3767 000049E6 07                  <1> 	pop	es
  3768 000049E7 5F                  <1> 	pop	edi
  3769 000049E8 5E                  <1> 	pop	esi
  3770 000049E9 59                  <1> 	pop	ecx
  3771 000049EA 7345                <1> 	jnc	short int33h_5
  3772 000049EC 8B1D[0C6B0100]      <1> 	mov	ebx, [user_buffer] ; 01/06/2016
  3773 000049F2 1F                  <1> 	pop	ds
  3774                              <1> 
  3775                              <1> 	;;15/01/2017
  3776                              <1> 	; 02/01/2017
  3777                              <1> 	;cli
  3778                              <1> 	;;mov	byte [ss:intflg], 0 ; 07/01/2017
  3779                              <1> 	;
  3780                              <1> 	; (*) 29/05/2016
  3781                              <1> 	; (*) retf 4 ; skip eflags on stack
  3782                              <1> 
  3783                              <1> 	; 29/05/2016 -set carry flag on stack-
  3784                              <1> 	; [esp] = EIP
  3785                              <1> 	; [esp+4] = CS
  3786                              <1> 	; [esp+8] = E-FLAGS
  3787 000049F3 804C240801          <1> 	or	byte [esp+8], 1  ; set carry bit of eflags register
  3788                              <1> 	; [esp+12] = ESP (user)
  3789                              <1> 	; [esp+16] = SS (User)
  3790 000049F8 B8FF000000          <1> 	mov	eax, 0FFh ; Unknown error !?
  3791                              <1> 	;iretd
  3792 000049FD EB7E                <1> 	jmp	short int33h_7  ; 07/01/2017	
  3793                              <1> 
  3794                              <1> 	; (*) 29/05/2016 - 'ref 4' intruction causes to stack fault
  3795                              <1> 	; (OUTER-PRIVILEGE-LEVEL)
  3796                              <1> 	; INTEL 80386 PROGRAMMER'S REFERENCE MANUAL 1986
  3797                              <1> 	; // RETF instruction:
  3798                              <1> 	;
  3799                              <1> 	; IF OperandMode=32 THEN
  3800                              <1>  	;    Load CS:EIP from stack;
  3801                              <1>  	;    Set CS RPL to CPL;
  3802                              <1>  	;    Increment eSP by 8 plus the immediate offset if it exists;
  3803                              <1>  	;    Load SS:eSP from stack;
  3804                              <1>  	; ELSE (* OperandMode=16 *)
  3805                              <1>  	;    Load CS:IP from stack;
  3806                              <1>  	;    Set CS RPL to CPL;
  3807                              <1>  	;    Increment eSP by 4 plus the immediate offset if it exists;
  3808                              <1> 	;    Load SS:eSP from stack;
  3809                              <1>  	; FI;
  3810                              <1> 	;
  3811                              <1> 	; //
  3812                              <1> 
  3813                              <1> int33h_2:
  3814 000049FF 80FC05              <1> 	cmp	ah, 05h ; format track
  3815 00004A02 770A                <1> 	ja	short int33h_3
  3816 00004A04 722B                <1> 	jb	short int33h_5
  3817 00004A06 51                  <1> 	push	ecx
  3818 00004A07 B901000000          <1> 	mov	ecx, 1
  3819 00004A0C EBBA                <1> 	jmp	short int33h_1
  3820                              <1> int33h_3:
  3821 00004A0E 80FC1C              <1> 	cmp	ah, 1Ch ; LBA write
  3822 00004A11 771E                <1> 	ja	short int33h_5
  3823 00004A13 74AF                <1> 	je	short int33h_0
  3824 00004A15 80FC1B              <1> 	cmp	ah, 1Bh ; LBA read
  3825 00004A18 7412                <1> 	je	short int33h_4
  3826                              <1> 	; 29/08/2020
  3827 00004A1A 80FC08              <1> 	cmp	ah, 08h ; get disk parameters
  3828                              <1> 	;jne	short int33h_5
  3829 00004A1D 7405                <1> 	je	short int33h_10
  3830 00004A1F 80FC15              <1> 	cmp	ah, 15h	; read DASD type (get disk size)
  3831 00004A22 750D                <1> 	jne	short int33h_5
  3832                              <1> int33h_10:
  3833                              <1> 	; 01/06/2016
  3834 00004A24 8B1D[0C6B0100]      <1> 	mov	ebx, [user_buffer] ; user's buffer address
  3835 00004A2A EB0A                <1> 	jmp	short int33h_6
  3836                              <1> int33h_4:
  3837 00004A2C A2[46640100]        <1> 	mov	byte [scount], al ; <= 128 sectors
  3838                              <1> int33h_5:
  3839 00004A31 BB00000700          <1> 	mov	ebx, Cluster_Buffer ; max. 65536 bytes
  3840                              <1> 				    ; buf. addr: 70000h	
  3841                              <1> 	;mov	byte [ClusterBuffer_Valid], 0
  3842                              <1> int33h_6:
  3843 00004A36 1F                  <1> 	pop	ds
  3844 00004A37 9C                  <1> 	pushfd
  3845 00004A38 0E                  <1> 	push 	cs
  3846 00004A39 E84D000000          <1> 	call 	DISK_IO
  3847 00004A3E 2E8B1D[0C6B0100]    <1> 	mov	ebx, [CS:user_buffer] ; 01/06/2016
  3848 00004A45 723D                <1> 	jc	short int33h_9
  3849                              <1> 	;
  3850 00004A47 2E803D[46640100]00  <1> 	cmp	byte [CS:scount], 0
  3851 00004A4F 762C                <1> 	jna	short int33h_7
  3852                              <1> 	;
  3853                              <1> 	; transfer sector buffer content to user's buffer
  3854 00004A51 06                  <1> 	push	es
  3855 00004A52 1E                  <1> 	push	ds
  3856 00004A53 50                  <1> 	push	eax
  3857 00004A54 66B81000            <1> 	mov	ax, KDATA
  3858 00004A58 8ED8                <1> 	mov	ds, ax
  3859 00004A5A 8EC0                <1> 	mov	es, ax
  3860 00004A5C 51                  <1> 	push	ecx
  3861 00004A5D 56                  <1> 	push	esi
  3862 00004A5E 57                  <1> 	push	edi
  3863 00004A5F 0FB60D[46640100]    <1> 	movzx	ecx, byte [scount]
  3864 00004A66 C1E109              <1> 	shl	ecx, 9 ; * 512 bytes
  3865 00004A69 89DF                <1> 	mov	edi, ebx ; user's buffer address
  3866 00004A6B BE00000700          <1> 	mov	esi, Cluster_Buffer
  3867 00004A70 E8EDA20000          <1> 	call	transfer_to_user_buffer
  3868 00004A75 5F                  <1> 	pop	edi
  3869 00004A76 5E                  <1> 	pop	esi
  3870 00004A77 59                  <1> 	pop	ecx
  3871 00004A78 58                  <1> 	pop	eax
  3872 00004A79 1F                  <1> 	pop	ds
  3873 00004A7A 07                  <1> 	pop	es
  3874 00004A7B 7202                <1> 	jc	short int33h_8
  3875                              <1> int33h_7:
  3876 00004A7D FA                  <1> 	cli
  3877                              <1> 	;;15/01/2017
  3878                              <1> 	;;mov	byte [ss:intflg], 0 ; 07/01/2017
  3879                              <1> 	; cf = 0  ; use eflags which is in stack
  3880 00004A7E CF                  <1> 	iretd	
  3881                              <1> int33h_8:
  3882 00004A7F B8FF000000          <1> 	mov	eax, 0FFh ; Unknown error !?
  3883                              <1> int33h_9:
  3884                              <1> 	; cf = 1
  3885                              <1> 
  3886                              <1> 	; (*) 29/05/2016	
  3887                              <1> 	; (*) retf 4 ; skip eflags on stack
  3888                              <1> 	; Note: This 'retf 4' was wrong, -it was causing
  3889                              <1> 	;       to stack errors in ring 3-
  3890                              <1> 	;	POP sequence of 'retf 4' is as
  3891                              <1> 	;       "eip, cs, eflags, esp, ss, +4 bytes" 
  3892                              <1>         ;       it is not as "eip, cs, +4 bytes, esp, ss" ! 
  3893                              <1> 
  3894                              <1> 	; 29/05/2016 -set carry flag on stack-
  3895 00004A84 804C240801          <1> 	or	byte [esp+8], 1  ; set carry bit of eflags register
  3896                              <1> 	;iretd
  3897 00004A89 EBF2                <1> 	jmp	short int33h_7 ; 07/01/2017
  3898                              <1> 
  3899                              <1> ; 30/08/2020
  3900                              <1> ; 09/12/2017
  3901                              <1> ; 29/05/2016
  3902                              <1> ; 27/05/2016 - TRDOS 386 (TRDOS v2.0)
  3903                              <1> 
  3904                              <1> DISK_IO:
  3905 00004A8B 80FA80              <1> 	CMP	DL,80H			; TEST FOR FIXED DISK DRIVE
  3906                              <1> 	;JAE	short A1		; YES, HANDLE HERE
  3907                              <1> 	;;;INT	40H			; DISKETTE HANDLER
  3908                              <1> 	;;call	int40h
  3909 00004A8E 0F82FFEFFFFF        <1> 	jb	DISKETTE_IO_1
  3910                              <1> ;RET_2:
  3911                              <1> 	;RETf	2			; BACK TO CALLER
  3912                              <1> ;	retf	4
  3913                              <1> A1:
  3914 00004A94 FB                  <1> 	STI				; ENABLE INTERRUPTS
  3915                              <1> 	;; 04/01/2015
  3916                              <1> 	;;OR	AH,AH
  3917                              <1> 	;;JNZ	short A2
  3918                              <1> 	;;INT	40H			; RESET NEC WHEN AH=0
  3919                              <1> 	;;SUB	AH,AH
  3920 00004A95 80FA83              <1> 	CMP	DL,(80H + S_MAX_FILE - 1) ; 83h ; 30/08/2020 
  3921                              <1> 	;JA	short RET_2
  3922 00004A98 7614                <1> 	jna	short _A0
  3923                              <1> 	; 29/05/2016
  3924 00004A9A 1E                  <1> 	push	ds
  3925 00004A9B 50                  <1> 	push	eax ; 30/08/2020 (ax --> eax)
  3926 00004A9C 66B81000            <1> 	mov	ax, KDATA
  3927 00004AA0 8ED8                <1> 	mov	ds, ax
  3928 00004AA2 58                  <1> 	pop	eax ; 
  3929 00004AA3 B4AA                <1>         mov     ah, 0AAh        ; Hard disk drive not ready !
  3930                              <1> 				; (Programmer's guide to AMIBIOS, 1992)
  3931 00004AA5 8825[1B5F0100]      <1> 	mov     byte [DISK_STATUS1], ah
  3932 00004AAB 1F                  <1> 	pop	ds
  3933 00004AAC EB38                <1> 	jmp	short RET_2
  3934                              <1> _A0:
  3935                              <1> 	; 18/01/2015
  3936 00004AAE 08E4                <1> 	or	ah,ah
  3937 00004AB0 743A                <1> 	jz	short A4
  3938 00004AB2 80FC0D              <1> 	cmp	ah,0Dh	; Alternate reset
  3939 00004AB5 7504                <1> 	jne	short A2
  3940 00004AB7 28E4                <1> 	sub	ah,ah	; Reset
  3941 00004AB9 EB31                <1> 	jmp	short A4
  3942                              <1> A2:
  3943 00004ABB 80FC08              <1> 	CMP	AH,08H			; GET PARAMETERS IS A SPECIAL CASE
  3944                              <1> 	;JNZ	short A3
  3945                              <1>         ;JMP    GET_PARM_N
  3946 00004ABE 0F8452030000        <1> 	je	GET_PARM_N
  3947 00004AC4 80FC15              <1> A3:	CMP	AH,15H			; READ DASD TYPE IS ALSO
  3948                              <1> 	;JNZ	short A4
  3949                              <1>         ;JMP    READ_DASD_TYPE
  3950 00004AC7 0F84DB020000        <1>         je      READ_DASD_TYPE
  3951                              <1> 	; 02/02/2015
  3952 00004ACD 80FC1D              <1> 	cmp	ah, 1Dh			;(Temporary for Retro UNIX 386 v1)
  3953                              <1> 	; 12/01/2015
  3954 00004AD0 F5                  <1> 	cmc
  3955 00004AD1 7319                <1> 	jnc	short A4
  3956                              <1> int33h_bad_cmd:
  3957                              <1> 	; 16/05/2016
  3958                              <1> 	; 30/01/2015
  3959                              <1> 	; 29/05/2016
  3960 00004AD3 1E                  <1> 	push	ds
  3961 00004AD4 6650                <1> 	push	ax
  3962 00004AD6 66B81000            <1> 	mov	ax, KDATA
  3963 00004ADA 8ED8                <1> 	mov	ds, ax
  3964 00004ADC 6658                <1> 	pop	ax
  3965 00004ADE B401                <1> 	mov	ah, BAD_CMD
  3966 00004AE0 8825[1B5F0100]      <1> 	mov     [DISK_STATUS1], ah ; BAD_CMD  ; COMMAND ERROR
  3967                              <1>         ;jmp	short RET_2
  3968                              <1> RET_2:
  3969                              <1> 	; (*) 29/05/2016
  3970                              <1> 	; (*) retf 4
  3971 00004AE6 804C240801          <1> 	or	byte [esp+8], 1 ; set carry bit of eflags register
  3972 00004AEB CF                  <1> 	iretd
  3973                              <1> A4:					; SAVE REGISTERS DURING OPERATION
  3974 00004AEC C8080000            <1> 	ENTER	8,0			; SAVE (BP) AND MAKE ROOM FOR @CMD_BLOCK
  3975 00004AF0 53                  <1> 	PUSH	eBX			;  IN THE STACK, THE COMMAND BLOCK IS:
  3976 00004AF1 51                  <1> 	PUSH	eCX			;   @CMD_BLOCK == BYTE PTR [BP]-8
  3977 00004AF2 52                  <1> 	PUSH	eDX
  3978 00004AF3 1E                  <1> 	PUSH	DS
  3979 00004AF4 06                  <1> 	PUSH	ES
  3980 00004AF5 56                  <1> 	PUSH	eSI
  3981 00004AF6 57                  <1> 	PUSH	eDI
  3982                              <1> 	;;04/01/2015
  3983                              <1> 	;;OR	AH,AH			; CHECK FOR RESET
  3984                              <1> 	;;JNZ	short A5
  3985                              <1> 	;;MOV	DL,80H			; FORCE DRIVE 80 FOR RESET
  3986                              <1> ;;A5:	
  3987                              <1> 	;push	cs
  3988                              <1> 	;pop	ds
  3989                              <1> 	; 21/02/2015
  3990 00004AF7 6650                <1> 	push	ax
  3991 00004AF9 66B81000            <1> 	mov	ax, KDATA
  3992 00004AFD 8ED8                <1> 	mov	ds, ax
  3993 00004AFF 8EC0                <1> 	mov	es, ax	
  3994 00004B01 6658                <1> 	pop	ax
  3995 00004B03 E88D000000          <1> 	CALL	DISK_IO_CONT		; PERFORM THE OPERATION
  3996                              <1> 	;;CALL	DDS			; ESTABLISH SEGMENT
  3997 00004B08 8A25[1B5F0100]      <1> 	MOV	AH,[DISK_STATUS1]	; GET STATUS FROM OPERATION
  3998                              <1> 	;(*) CMP AH,1			; SET THE CARRY FLAG TO INDICATE
  3999                              <1> 	;(*) CMC			; SUCCESS OR FAILURE
  4000 00004B0E 5F                  <1> 	POP	eDI			; RESTORE REGISTERS
  4001 00004B0F 5E                  <1> 	POP	eSI
  4002 00004B10 07                  <1>         POP     ES
  4003 00004B11 1F                  <1>         POP     DS
  4004 00004B12 5A                  <1> 	POP	eDX
  4005 00004B13 59                  <1> 	POP	eCX
  4006 00004B14 5B                  <1> 	POP	eBX
  4007 00004B15 C9                  <1> 	LEAVE				; ADJUST (SP) AND RESTORE (BP)
  4008                              <1> 	;RETf	2			; THROW AWAY SAVED FLAGS
  4009                              <1> 	; (*) 29/05/2016
  4010                              <1> 	; (*) retf 4
  4011 00004B16 80FC01              <1> 	cmp	ah, 1
  4012 00004B19 7205                <1> 	jc	short _A5 
  4013 00004B1B 804C240801          <1> 	or	byte [esp+8], 1 ; set carry bit of eflags register
  4014                              <1> _A5:
  4015 00004B20 CF                  <1> 	iretd
  4016                              <1> 
  4017                              <1> ; 21/02/2015
  4018                              <1> ;       dw --> dd
  4019                              <1> D1:					; FUNCTION TRANSFER TABLE
  4020 00004B21 [E44C0000]          <1> 	dd	DISK_RESET		; 000H
  4021 00004B25 [5B4D0000]          <1> 	dd	RETURN_STATUS		; 001H
  4022 00004B29 [684D0000]          <1> 	dd	DISK_READ		; 002H
  4023 00004B2D [714D0000]          <1> 	dd	DISK_WRITE		; 003H
  4024 00004B31 [7A4D0000]          <1> 	dd	DISK_VERF		; 004H
  4025 00004B35 [924D0000]          <1> 	dd	FMT_TRK 		; 005H
  4026 00004B39 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 006H	FORMAT BAD SECTORS
  4027 00004B3D [DA4C0000]          <1> 	dd	BAD_COMMAND		; 007H	FORMAT DRIVE
  4028 00004B41 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 008H	RETURN PARAMETERS
  4029 00004B45 [AF4E0000]          <1> 	dd	INIT_DRV		; 009H
  4030 00004B49 [0E4F0000]          <1> 	dd	RD_LONG 		; 00AH
  4031 00004B4D [174F0000]          <1> 	dd	WR_LONG 		; 00BH
  4032 00004B51 [204F0000]          <1> 	dd	DISK_SEEK		; 00CH
  4033 00004B55 [E44C0000]          <1> 	dd	DISK_RESET		; 00DH
  4034 00004B59 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 00EH	READ BUFFER
  4035 00004B5D [DA4C0000]          <1> 	dd	BAD_COMMAND		; 00FH	WRITE BUFFER
  4036 00004B61 [484F0000]          <1> 	dd	TST_RDY 		; 010H
  4037 00004B65 [6C4F0000]          <1> 	dd	HDISK_RECAL		; 011H
  4038 00004B69 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 012H	MEMORY DIAGNOSTIC
  4039 00004B6D [DA4C0000]          <1> 	dd	BAD_COMMAND		; 013H	DRIVE DIAGNOSTIC
  4040 00004B71 [A24F0000]          <1> 	dd	CTLR_DIAGNOSTIC 	; 014H	CONTROLLER DIAGNOSTIC
  4041                              <1> 	; 02/02/2015 (Temporary - Retro UNIX 386 v1 - DISK I/O test)
  4042 00004B75 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 015h
  4043 00004B79 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 016h
  4044 00004B7D [DA4C0000]          <1> 	dd	BAD_COMMAND		; 017h
  4045 00004B81 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 018h
  4046 00004B85 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 019h
  4047 00004B89 [DA4C0000]          <1> 	dd	BAD_COMMAND		; 01Ah
  4048 00004B8D [684D0000]          <1> 	dd	DISK_READ		; 01Bh ; LBA read
  4049 00004B91 [714D0000]          <1> 	dd	DISK_WRITE		; 01Ch ; LBA write
  4050                              <1> D1L     EQU    $ - D1
  4051                              <1> 
  4052                              <1> DISK_IO_CONT:
  4053                              <1> 	;;CALL	DDS			; ESTABLISH SEGMENT
  4054 00004B95 80FC01              <1> 	CMP	AH,01H			; RETURN STATUS
  4055                              <1> 	;;JNZ	short SU0
  4056                              <1>         ;;JMP	RETURN_STATUS
  4057 00004B98 0F84BD010000        <1> 	je	RETURN_STATUS
  4058                              <1> SU0:
  4059 00004B9E C605[1B5F0100]00    <1> 	MOV	byte [DISK_STATUS1],0 	; RESET THE STATUS INDICATOR
  4060                              <1> 	;;PUSH	BX			; SAVE DATA ADDRESS
  4061                              <1> 	;mov	si, bx ;; 14/02/2015
  4062 00004BA5 89DE                <1> 	mov	esi, ebx ; 21/02/2015
  4063 00004BA7 8A1D[1C5F0100]      <1> 	MOV	BL,[HF_NUM]		; GET NUMBER OF DRIVES
  4064                              <1> 	;; 04/01/2015
  4065                              <1> 	;;PUSH	AX
  4066 00004BAD 80E27F              <1> 	AND	DL,7FH			; GET DRIVE AS 0 OR 1
  4067                              <1> 					; (get drive number as 0 to 3)
  4068 00004BB0 38D3                <1> 	CMP	BL,DL
  4069                              <1>         ;;JBE   BAD_COMMAND_POP         ; INVALID DRIVE
  4070 00004BB2 0F8622010000        <1>         jbe     BAD_COMMAND ;; 14/02/2015
  4071                              <1>         ;
  4072                              <1> 	;;03/01/2015
  4073 00004BB8 29DB                <1> 	sub	ebx, ebx
  4074 00004BBA 88D3                <1> 	mov	bl, dl
  4075                              <1> 	;sub	bh, bh
  4076 00004BBC 883D[305F0100]      <1> 	mov	[LBAMode], bh 	; 0
  4077                              <1> 	;;test	byte [bx+hd0_type], 1	; LBA ready ?
  4078                              <1> 	;test	byte [ebx+hd0_type], 1
  4079                              <1> 	;jz	short su1		; no
  4080                              <1> 	;inc	byte [LBAMode]
  4081                              <1> ;su1:
  4082                              <1> 	; 21/02/2015 (32 bit modification)
  4083                              <1> 	;04/01/2015
  4084 00004BC2 6650                <1> 	push	ax ; ***
  4085                              <1> 	;PUSH	ES ; **
  4086 00004BC4 6652                <1> 	PUSH	DX ; *
  4087 00004BC6 6650                <1> 	push	ax
  4088 00004BC8 E8BB060000          <1> 	CALL	GET_VEC 		; GET DISK PARAMETERS
  4089                              <1> 	; 02/02/2015
  4090                              <1> 	;mov	ax, [ES:BX+16] ; I/O port base address (1F0h, 170h)
  4091 00004BCD 668B4310            <1> 	mov	ax, [ebx+16]
  4092 00004BD1 66A3[A0640000]      <1> 	mov	[HF_PORT], ax
  4093                              <1> 	;mov	dx, [ES:BX+18] ; control port address (3F6h, 376h)
  4094 00004BD7 668B5312            <1> 	mov	dx, [ebx+18]
  4095 00004BDB 668915[A2640000]    <1> 	mov	[HF_REG_PORT], dx
  4096                              <1> 	;mov	al, [ES:BX+20] ; head register upper nibble (A0h,B0h,E0h,F0h)
  4097 00004BE2 8A4314              <1> 	mov	al, [ebx+20]
  4098                              <1> 	; 23/02/2015
  4099 00004BE5 A840                <1> 	test	al, 40h	 ; LBA bit (bit 6)
  4100 00004BE7 7406                <1> 	jz 	short su1
  4101 00004BE9 FE05[305F0100]      <1> 	inc	byte [LBAMode] ; 1 
  4102                              <1> su1: 	 
  4103 00004BEF C0E804              <1> 	shr 	al, 4
  4104 00004BF2 2401                <1> 	and	al, 1			
  4105 00004BF4 A2[A4640000]        <1> 	mov	[hf_m_s], al 
  4106                              <1> 	;
  4107                              <1> 	; 03/01/2015
  4108                              <1> 	;MOV	AL,byte [ES:BX+8]	; GET CONTROL BYTE MODIFIER
  4109 00004BF9 8A4308              <1> 	mov	al, [ebx+8]
  4110                              <1> 	;MOV	DX,[HF_REG_PORT]	; Device Control register	
  4111 00004BFC EE                  <1> 	OUT	DX,AL			; SET EXTRA HEAD OPTION
  4112                              <1> 					; Control Byte:  (= 08h, here)
  4113                              <1> 					; bit 0 - 0
  4114                              <1> 					; bit 1 - nIEN (1 = disable irq)
  4115                              <1> 					; bit 2 - SRST (software RESET)
  4116                              <1> 					; bit 3 - use extra heads (8 to 15)
  4117                              <1> 					;         -always set to 1-	
  4118                              <1> 					; (bits 3 to 7 are reserved
  4119                              <1> 					;          for ATA devices)
  4120 00004BFD 8A25[1D5F0100]      <1> 	MOV	AH,[CONTROL_BYTE]	; SET EXTRA HEAD OPTION IN
  4121 00004C03 80E4C0              <1> 	AND	AH,0C0H 		; CONTROL BYTE
  4122 00004C06 08C4                <1> 	OR	AH,AL
  4123 00004C08 8825[1D5F0100]      <1> 	MOV	[CONTROL_BYTE],AH	
  4124                              <1> 	; 04/01/2015
  4125 00004C0E 6658                <1> 	pop	ax
  4126 00004C10 665A                <1> 	pop	dx ; * ;; 14/02/2015
  4127 00004C12 20E4                <1> 	and	ah, ah	; Reset function ?
  4128 00004C14 7507                <1> 	jnz	short su2
  4129                              <1> 	;;pop	dx ; * ;; 14/02/2015
  4130                              <1> 	;pop	es ; **
  4131 00004C16 6658                <1> 	pop	ax ; ***
  4132                              <1> 	;;pop	bx
  4133 00004C18 E9C7000000          <1>         jmp     DISK_RESET
  4134                              <1> su2:
  4135 00004C1D 803D[305F0100]00    <1> 	cmp	byte [LBAMode], 0
  4136 00004C24 7662                <1> 	jna	short su3
  4137                              <1> 	;
  4138                              <1> 	; 02/02/2015 (LBA read/write function calls)
  4139 00004C26 80FC1B              <1> 	cmp	ah, 1Bh
  4140 00004C29 720B                <1> 	jb	short lbarw1
  4141 00004C2B 80FC1C              <1> 	cmp	ah, 1Ch
  4142 00004C2E 775D                <1> 	ja 	short invldfnc
  4143                              <1> 	;;pop	dx ; * ; 14/02/2015
  4144                              <1> 	;mov	ax, cx ; Lower word of LBA address (bits 0-15)
  4145 00004C30 89C8                <1> 	mov	eax, ecx ; LBA address (21/02/2015)
  4146                              <1> 	;; 14/02/2015
  4147 00004C32 88D1                <1> 	mov	cl, dl ; 14/02/2015
  4148                              <1> 	;;mov	dx, bx
  4149                              <1> 	;mov	dx, si ; higher word of LBA address (bits 16-23)
  4150                              <1> 	;;mov	bx, di
  4151                              <1> 	;mov	si, di ; Buffer offset
  4152 00004C34 EB32                <1> 	jmp	short lbarw2
  4153                              <1> lbarw1:
  4154                              <1> 	; convert CHS to LBA
  4155                              <1> 	;
  4156                              <1> 	; LBA calculation - AWARD BIOS - 1999 - AHDSK.ASM
  4157                              <1> 	; LBA = "# of Heads" * Sectors/Track * Cylinder + Head * Sectors/Track
  4158                              <1> 	;	+ Sector - 1
  4159 00004C36 6652                <1> 	push	dx ; * ;; 14/02/2015
  4160                              <1> 	;xor	dh, dh
  4161 00004C38 31D2                <1> 	xor	edx, edx
  4162                              <1> 	;mov	dl, [ES:BX+14]	; sectors per track (logical)
  4163 00004C3A 8A530E              <1> 	mov	dl, [ebx+14]
  4164                              <1> 	;xor	ah, ah
  4165 00004C3D 31C0                <1> 	xor	eax, eax
  4166                              <1> 	;mov	al, [ES:BX+2]	; heads (logical) 	
  4167 00004C3F 8A4302              <1> 	mov	al, [ebx+2]
  4168 00004C42 FEC8                <1> 	dec	al
  4169 00004C44 6640                <1> 	inc	ax		; 0 =  256
  4170 00004C46 66F7E2              <1> 	mul 	dx
  4171                              <1> 		; AX = # of Heads" * Sectors/Track
  4172 00004C49 6689CA              <1> 	mov	dx, cx
  4173                              <1> 	;and	cx, 3Fh	 ; sector  (1 to 63)
  4174 00004C4C 83E13F              <1> 	and	ecx, 3fh
  4175 00004C4F 86D6                <1> 	xchg	dl, dh
  4176 00004C51 C0EE06              <1> 	shr	dh, 6
  4177                              <1> 		; DX = cylinder (0 to 1023)
  4178                              <1> 	;mul 	dx
  4179                              <1> 		; DX:AX = # of Heads" * Sectors/Track * Cylinder
  4180 00004C54 F7E2                <1> 	mul	edx
  4181 00004C56 FEC9                <1> 	dec	cl  ; sector - 1
  4182                              <1> 	;add	ax, cx
  4183                              <1> 	;adc	dx, 0
  4184                              <1> 		; DX:AX = # of Heads" * Sectors/Track * Cylinder + Sector -1
  4185 00004C58 01C8                <1> 	add	eax, ecx
  4186 00004C5A 6659                <1> 	pop	cx ; * ; ch = head, cl = drive number (zero based)
  4187                              <1> 	;push	dx
  4188                              <1> 	;push	ax
  4189 00004C5C 50                  <1> 	push	eax
  4190                              <1> 	;mov	al, [ES:BX+14]	; sectors per track (logical)	
  4191 00004C5D 8A430E              <1> 	mov	al, [ebx+14]
  4192 00004C60 F6E5                <1> 	mul	ch
  4193                              <1> 		;  AX = Head * Sectors/Track
  4194 00004C62 0FB7C0              <1>         movzx	eax, ax ; 09/12/2017
  4195                              <1> 	;pop	dx
  4196 00004C65 5A                  <1> 	pop	edx
  4197                              <1> 	;add	ax, dx
  4198                              <1> 	;pop	dx
  4199                              <1> 	;adc	dx, 0 ; add carry bit
  4200 00004C66 01D0                <1> 	add	eax, edx
  4201                              <1> lbarw2:
  4202 00004C68 29D2                <1> 	sub	edx, edx ; 21/02/2015
  4203 00004C6A 88CA                <1> 	mov	dl, cl ; 21/02/2015
  4204 00004C6C C645F800            <1>         mov     byte [CMD_BLOCK], 0 ; Features Register
  4205                              <1> 				; NOTE: Features register (1F1h, 171h)
  4206                              <1> 				; is not used for ATA device R/W functions. 
  4207                              <1> 				; It is old/obsolete 'write precompensation'
  4208                              <1> 				; register and error register
  4209                              <1> 				; for old ATA/IDE devices.
  4210                              <1> 	; 18/01/2014
  4211                              <1> 	;mov	ch, [hf_m_s]	; Drive 0 (master) or 1 (slave)
  4212 00004C70 8A0D[A4640000]      <1> 	mov	cl, [hf_m_s]
  4213                              <1> 	;shl	ch, 4		; bit 4 (drive bit)
  4214                              <1> 	;or	ch, 0E0h	; bit 5 = 1
  4215                              <1> 				; bit 6 = 1 = LBA mode
  4216                              <1> 				; bit 7 = 1
  4217 00004C76 80C90E              <1> 	or	cl, 0Eh ; 1110b
  4218                              <1> 	;and	dh, 0Fh		; LBA byte 4 (bits 24 to 27)
  4219 00004C79 25FFFFFF0F          <1> 	and	eax, 0FFFFFFFh
  4220 00004C7E C1E11C              <1> 	shl	ecx, 28 ; 21/02/2015
  4221                              <1> 	;or	dh, ch
  4222 00004C81 09C8                <1> 	or	eax, ecx	
  4223                              <1> 	;;mov	[CMD_BLOCK+2], al ; LBA byte 1 (bits 0 to 7)
  4224                              <1> 				  ; (Sector Number Register)
  4225                              <1> 	;;mov	[CMD_BLOCK+3], ah ; LBA byte 2 (bits 8 to 15)
  4226                              <1> 				  ; (Cylinder Low Register)
  4227                              <1> 	;mov	[CMD_BLOCK+2], ax ; LBA byte 1, 2
  4228                              <1> 	;mov	[CMD_BLOCK+4], dl ; LBA byte 3 (bits 16 to 23)
  4229                              <1> 				  ; (Cylinder High Register)
  4230                              <1> 	;;mov	[CMD_BLOCK+5], dh ; LBA byte 4 (bits 24 to 27)
  4231                              <1> 				  ; (Drive/Head Register)
  4232                              <1> 	
  4233                              <1> 	;mov	[CMD_BLOCK+4], dx ; LBA byte 4, LBA & DEV select bits
  4234 00004C83 8945FA              <1> 	mov	[CMD_BLOCK+2], eax ; 21/02/2015
  4235                              <1> 	;14/02/2015
  4236                              <1> 	;mov	dl, cl ; Drive number (INIT_DRV)		
  4237 00004C86 EB38                <1> 	jmp	short su4
  4238                              <1> su3:
  4239                              <1> 	; 02/02/2015 
  4240                              <1> 	; (Temporary functions 1Bh & 1Ch are not valid for CHS mode) 
  4241 00004C88 80FC14              <1> 	cmp 	ah, 14h
  4242 00004C8B 7604                <1> 	jna 	short chsfnc
  4243                              <1> invldfnc:
  4244                              <1>         ; 14/02/2015  
  4245                              <1> 	;pop	es ; **
  4246 00004C8D 6658                <1>         pop     ax ; ***
  4247                              <1>         ;jmp     short BAD_COMMAND_POP
  4248 00004C8F EB49                <1>         jmp     short BAD_COMMAND
  4249                              <1> chsfnc:	
  4250                              <1> 	;MOV	AX,[ES:BX+5]		; GET WRITE PRE-COMPENSATION CYLINDER
  4251 00004C91 668B4305            <1> 	mov	ax, [ebx+5]
  4252 00004C95 66C1E802            <1> 	SHR	AX,2
  4253 00004C99 8845F8              <1> 	MOV	[CMD_BLOCK],AL
  4254                              <1> 	;;MOV	AL,[ES:BX+8]		; GET CONTROL BYTE MODIFIER
  4255                              <1> 	;;PUSH	DX
  4256                              <1> 	;;MOV	DX,[HF_REG_PORT]
  4257                              <1> 	;;OUT	DX,AL			; SET EXTRA HEAD OPTION
  4258                              <1> 	;;POP	DX ; * 
  4259                              <1> 	;;POP	ES ; **
  4260                              <1> 	;;MOV	AH,[CONTROL_BYTE]	; SET EXTRA HEAD OPTION IN
  4261                              <1> 	;;AND	AH,0C0H 		; CONTROL BYTE	
  4262                              <1> 	;;OR	AH,AL
  4263                              <1> 	;;MOV	[CONTROL_BYTE],AH
  4264                              <1> 	;
  4265 00004C9C 88C8                <1> 	MOV	AL,CL			; GET SECTOR NUMBER
  4266 00004C9E 243F                <1> 	AND	AL,3FH
  4267 00004CA0 8845FA              <1> 	MOV	[CMD_BLOCK+2],AL
  4268 00004CA3 886DFB              <1> 	MOV	[CMD_BLOCK+3],CH 	; GET CYLINDER NUMBER
  4269 00004CA6 88C8                <1> 	MOV	AL,CL
  4270 00004CA8 C0E806              <1> 	SHR	AL,6
  4271 00004CAB 8845FC              <1> 	MOV	[CMD_BLOCK+4],AL 	; CYLINDER HIGH ORDER 2 BITS
  4272                              <1> 	;;05/01/2015
  4273                              <1> 	;;MOV	AL,DL			; DRIVE NUMBER
  4274 00004CAE A0[A4640000]        <1> 	mov	al, [hf_m_s]
  4275 00004CB3 C0E004              <1> 	SHL	AL,4
  4276 00004CB6 80E60F              <1> 	AND	DH,0FH			; HEAD NUMBER
  4277 00004CB9 08F0                <1> 	OR	AL,DH
  4278                              <1> 	;OR	AL,80H or 20H
  4279 00004CBB 0CA0                <1> 	OR	AL,80h+20h		; ECC AND 512 BYTE SECTORS
  4280 00004CBD 8845FD              <1> 	MOV	[CMD_BLOCK+5],AL 	; ECC/SIZE/DRIVE/HEAD
  4281                              <1> su4:
  4282                              <1> 	;POP	ES ; **
  4283                              <1>         ;; 14/02/2015
  4284                              <1>         ;;POP   AX
  4285                              <1>         ;;MOV   [CMD_BLOCK+1],AL        ; SECTOR COUNT
  4286                              <1>         ;;PUSH  AX
  4287                              <1>         ;;MOV   AL,AH                   ; GET INTO LOW BYTE
  4288                              <1>         ;;XOR   AH,AH                   ; ZERO HIGH BYTE
  4289                              <1>         ;;SAL   AX,1                    ; *2 FOR TABLE LOOKUP
  4290 00004CC0 6658                <1>         pop     ax ; ***
  4291 00004CC2 8845F9              <1>         mov     [CMD_BLOCK+1], al
  4292 00004CC5 29DB                <1>         sub	ebx, ebx
  4293 00004CC7 88E3                <1> 	mov     bl, ah
  4294                              <1>         ;xor     bh, bh
  4295                              <1>         ;sal     bx, 1
  4296 00004CC9 66C1E302            <1>         sal	bx, 2	; 32 bit offset (21/02/2015)
  4297                              <1> 	;;MOV   SI,AX                   ; PUT INTO SI FOR BRANCH
  4298                              <1>         ;;CMP   AX,D1L                  ; TEST WITHIN RANGE
  4299                              <1>         ;;JNB   short BAD_COMMAND_POP
  4300                              <1>         ;cmp     bx, D1L
  4301 00004CCD 83FB74              <1> 	cmp	ebx, D1L
  4302 00004CD0 7308                <1> 	jnb	short BAD_COMMAND
  4303                              <1>         ;xchg    bx, si
  4304 00004CD2 87DE                <1>         xchg	ebx, esi
  4305                              <1> 	;;;POP	AX			; RESTORE AX
  4306                              <1> 	;;;POP	BX			; AND DATA ADDRESS
  4307                              <1> 	
  4308                              <1> 	;;PUSH	CX
  4309                              <1> 	;;PUSH	AX			; ADJUST ES:BX
  4310                              <1> 	;MOV	CX,BX			; GET 3 HIGH ORDER NIBBLES OF BX
  4311                              <1> 	;SHR	CX,4
  4312                              <1> 	;MOV	AX,ES
  4313                              <1> 	;ADD	AX,CX
  4314                              <1> 	;MOV	ES,AX
  4315                              <1> 	;AND	BX,000FH		; ES:BX CHANGED TO ES:000X
  4316                              <1> 	;;POP	AX
  4317                              <1> 	;;POP	CX
  4318                              <1> 	;;JMP	word [CS:SI+D1]
  4319                              <1> 	;jmp	word [SI+D1]
  4320 00004CD4 FFA6[214B0000]      <1> 	jmp	dword [esi+D1]
  4321                              <1> ;;BAD_COMMAND_POP:
  4322                              <1> ;;	POP	AX
  4323                              <1> ;;	POP	BX
  4324                              <1> BAD_COMMAND:
  4325 00004CDA C605[1B5F0100]01    <1>         MOV     byte [DISK_STATUS1],BAD_CMD  ; COMMAND ERROR
  4326 00004CE1 B000                <1> 	MOV	AL,0
  4327 00004CE3 C3                  <1> 	RETn
  4328                              <1> 
  4329                              <1> ;----------------------------------------
  4330                              <1> ;	RESET THE DISK SYSTEM  (AH=00H) :
  4331                              <1> ;----------------------------------------
  4332                              <1> 
  4333                              <1> ; 18-1-2015 : one controller reset (not other one)
  4334                              <1> 
  4335                              <1> DISK_RESET:
  4336 00004CE4 FA                  <1> 	CLI
  4337 00004CE5 E4A1                <1> 	IN	AL,INTB01		; GET THE MASK REGISTER
  4338                              <1> 	;JMP	$+2
  4339                              <1> 	IODELAY
  4339 00004CE7 EB00                <2>  jmp short $+2
  4339 00004CE9 EB00                <2>  jmp short $+2
  4340                              <1> 	;AND	AL,0BFH 		; ENABLE FIXED DISK INTERRUPT
  4341 00004CEB 243F                <1> 	and	al,3Fh			; 22/12/2014 (IRQ 14 & IRQ 15)
  4342 00004CED E6A1                <1> 	OUT	INTB01,AL
  4343 00004CEF FB                  <1> 	STI				; START INTERRUPTS
  4344                              <1> 	; 14/02/2015
  4345 00004CF0 6689D7              <1> 	mov	di, dx	
  4346                              <1> 	; 04/01/2015
  4347                              <1> 	;xor	di,di
  4348                              <1> drst0:
  4349 00004CF3 B004                <1> 	MOV	AL,04H  ; bit 2 - SRST 
  4350                              <1> 	;MOV	DX,HF_REG_PORT
  4351 00004CF5 668B15[A2640000]    <1> 	MOV	DX,[HF_REG_PORT]
  4352 00004CFC EE                  <1> 	OUT	DX,AL			; RESET
  4353                              <1> ;	MOV	CX,10			; DELAY COUNT
  4354                              <1> ;DRD:	DEC	CX
  4355                              <1> ;	JNZ	short DRD		; WAIT 4.8 MICRO-SEC
  4356                              <1> 	;mov	cx,2			; wait for 30 micro seconds	
  4357 00004CFD B902000000          <1>         mov	ecx, 2 ; 21/02/2015
  4358 00004D02 E811D5FFFF          <1> 	call    WAITF                   ; (Award Bios 1999 - WAIT_REFRESH,
  4359                              <1>                                         ; 40 micro seconds)
  4360 00004D07 A0[1D5F0100]        <1> 	mov	al,[CONTROL_BYTE]
  4361 00004D0C 240F                <1> 	AND	AL,0FH			; SET HEAD OPTION
  4362 00004D0E EE                  <1> 	OUT	DX,AL			; TURN RESET OFF
  4363 00004D0F E86A040000          <1> 	CALL	NOT_BUSY
  4364 00004D14 7515                <1> 	JNZ	short DRERR		; TIME OUT ON RESET
  4365 00004D16 668B15[A0640000]    <1> 	MOV	DX,[HF_PORT]
  4366 00004D1D FEC2                <1> 	inc	dl  ; HF_PORT+1
  4367                              <1> 	; 02/01/2015 - Award BIOS 1999 - AHDSK.ASM
  4368                              <1>         ;mov     cl, 10
  4369 00004D1F B90A000000          <1>         mov     ecx, 10 ; 21/02/2015 
  4370                              <1> drst1:
  4371 00004D24 EC                  <1> 	IN	AL,DX			; GET RESET STATUS
  4372 00004D25 3C01                <1> 	CMP	AL,1
  4373                              <1> 	; 04/01/2015
  4374 00004D27 740A                <1> 	jz	short drst2
  4375                              <1> 	;JNZ	short DRERR		; BAD RESET STATUS
  4376                              <1>         	; Drive/Head Register - bit 4
  4377 00004D29 E2F9                <1> 	loop	drst1
  4378                              <1> DRERR:	
  4379 00004D2B C605[1B5F0100]05    <1> 	MOV	byte [DISK_STATUS1],BAD_RESET ; CARD FAILED
  4380 00004D32 C3                  <1> 	RETn
  4381                              <1> drst2:
  4382                              <1> 	; 14/02/2015
  4383 00004D33 6689FA              <1> 	mov	dx,di
  4384                              <1> ;drst3:
  4385                              <1> ;	; 05/01/2015
  4386                              <1> ;	shl 	di,1
  4387                              <1> ;	; 04/01/2015
  4388                              <1> ;	mov	ax,[di+hd_cports]
  4389                              <1> ;	cmp	ax,[HF_REG_PORT]
  4390                              <1> ;	je	short drst4
  4391                              <1> ;	mov	[HF_REG_PORT], ax
  4392                              <1> ;	; 03/01/2015
  4393                              <1> ;	mov	ax,[di+hd_ports]
  4394                              <1> ;       mov     [HF_PORT], ax
  4395                              <1> ;	; 05/01/2014
  4396                              <1> ;	shr	di,1
  4397                              <1> ;	; 04/01/2015
  4398                              <1> ;	jmp	short drst0	; reset other controller
  4399                              <1> ;drst4:
  4400                              <1> ;	; 05/01/2015
  4401                              <1> ;	shr	di,1
  4402                              <1> ;	mov	al,[di+hd_dregs]
  4403                              <1> ;	and	al,10h ; bit 4 only
  4404                              <1> ;	shr	al,4 ; bit 4  -> bit 0
  4405                              <1> ;	mov	[hf_m_s], al ; (0 = master, 1 = slave)
  4406                              <1> 	;
  4407 00004D36 A0[A4640000]        <1> 	mov	al, [hf_m_s] ; 18/01/2015
  4408 00004D3B A801                <1> 	test	al,1
  4409                              <1> ;	jnz	short drst6
  4410 00004D3D 7516                <1>         jnz     short drst4
  4411 00004D3F 8065FDEF            <1> 	AND     byte [CMD_BLOCK+5],0EFH ; SET TO DRIVE 0
  4412                              <1> ;drst5:
  4413                              <1> drst3:
  4414 00004D43 E867010000          <1> 	CALL	INIT_DRV		; SET MAX HEADS
  4415                              <1> 	;mov	dx,di
  4416 00004D48 E81F020000          <1> 	CALL	HDISK_RECAL		; RECAL TO RESET SEEK SPEED
  4417                              <1> 	; 04/01/2014
  4418                              <1> ;	inc	di
  4419                              <1> ;	mov	dx,di
  4420                              <1> ;	cmp	dl,[HF_NUM]
  4421                              <1> ;	jb	short drst3
  4422                              <1> ;DRE:
  4423 00004D4D C605[1B5F0100]00    <1> 	MOV	byte [DISK_STATUS1],0 	; IGNORE ANY SET UP ERRORS
  4424 00004D54 C3                  <1> 	RETn
  4425                              <1> ;drst6:
  4426                              <1> drst4:		; Drive/Head Register - bit 4
  4427 00004D55 804DFD10            <1> 	OR      byte [CMD_BLOCK+5],010H ; SET TO DRIVE 1     
  4428                              <1>         ;jmp    short drst5
  4429 00004D59 EBE8                <1>         jmp     short drst3
  4430                              <1> 
  4431                              <1> ;----------------------------------------
  4432                              <1> ;	DISK STATUS ROUTINE  (AH = 01H) :
  4433                              <1> ;----------------------------------------
  4434                              <1> 
  4435                              <1> RETURN_STATUS:
  4436 00004D5B A0[1B5F0100]        <1> 	MOV	AL,[DISK_STATUS1]	; OBTAIN PREVIOUS STATUS
  4437 00004D60 C605[1B5F0100]00    <1>         MOV     byte [DISK_STATUS1],0   ; RESET STATUS
  4438 00004D67 C3                  <1> 	RETn
  4439                              <1> 
  4440                              <1> ;----------------------------------------
  4441                              <1> ;	DISK READ ROUTINE    (AH = 02H) :
  4442                              <1> ;----------------------------------------
  4443                              <1> 
  4444                              <1> DISK_READ:
  4445 00004D68 C645FE20            <1> 	MOV	byte [CMD_BLOCK+6],READ_CMD
  4446 00004D6C E986020000          <1>         JMP     COMMANDI
  4447                              <1> 
  4448                              <1> ;----------------------------------------
  4449                              <1> ;	DISK WRITE ROUTINE   (AH = 03H) :
  4450                              <1> ;----------------------------------------
  4451                              <1> 
  4452                              <1> DISK_WRITE:
  4453 00004D71 C645FE30            <1> 	MOV	byte [CMD_BLOCK+6],WRITE_CMD
  4454 00004D75 E9D8020000          <1>         JMP     COMMANDO
  4455                              <1> 
  4456                              <1> ;----------------------------------------
  4457                              <1> ;	DISK VERIFY	     (AH = 04H) :
  4458                              <1> ;----------------------------------------
  4459                              <1> 
  4460                              <1> DISK_VERF:
  4461 00004D7A C645FE40            <1> 	MOV	byte [CMD_BLOCK+6],VERIFY_CMD
  4462 00004D7E E846030000          <1> 	CALL	COMMAND
  4463 00004D83 750C                <1> 	JNZ	short VERF_EXIT		; CONTROLLER STILL BUSY
  4464 00004D85 E8B8030000          <1> 	CALL	_WAIT			; (Original: CALL WAIT)	
  4465 00004D8A 7505                <1> 	JNZ	short VERF_EXIT		; TIME OUT
  4466 00004D8C E845040000          <1> 	CALL	CHECK_STATUS
  4467                              <1> VERF_EXIT:
  4468 00004D91 C3                  <1> 	RETn
  4469                              <1> 
  4470                              <1> ;----------------------------------------
  4471                              <1> ;	FORMATTING	     (AH = 05H) :
  4472                              <1> ;----------------------------------------
  4473                              <1> 
  4474                              <1> FMT_TRK:				; FORMAT TRACK	(AH = 005H)
  4475 00004D92 C645FE50            <1> 	MOV	byte [CMD_BLOCK+6],FMTTRK_CMD
  4476                              <1> 	;PUSH	ES
  4477                              <1> 	;PUSH	BX
  4478 00004D96 53                  <1> 	push	ebx
  4479 00004D97 E8EC040000          <1> 	CALL	GET_VEC 		; GET DISK PARAMETERS ADDRESS
  4480                              <1> 	;MOV	AL,[ES:BX+14]		; GET SECTORS/TRACK
  4481 00004D9C 8A430E              <1> 	mov	al, [ebx+14]
  4482 00004D9F 8845F9              <1> 	MOV	[CMD_BLOCK+1],AL 	; SET SECTOR COUNT IN COMMAND
  4483 00004DA2 5B                  <1> 	pop	ebx
  4484                              <1> 	;POP	BX
  4485                              <1> 	;POP	ES
  4486 00004DA3 E9B1020000          <1>         JMP     CMD_OF                  ; GO EXECUTE THE COMMAND
  4487                              <1> 
  4488                              <1> ; 30/08/2020
  4489                              <1> 
  4490                              <1> ;----------------------------------------
  4491                              <1> ;	READ DASD TYPE	     (AH = 15H) :
  4492                              <1> ;----------------------------------------
  4493                              <1> 
  4494                              <1> READ_DASD_TYPE:
  4495                              <1> READ_D_T:				; GET DRIVE PARAMETERS
  4496 00004DA8 1E                  <1> 	PUSH	DS			; SAVE REGISTERS
  4497                              <1> 	;PUSH	ES
  4498 00004DA9 53                  <1> 	PUSH	eBX
  4499                              <1> 	;CALL	DDS			; ESTABLISH ADDRESSING
  4500                              <1> 	;push	cs
  4501                              <1> 	;pop	ds
  4502 00004DAA 66BB1000            <1>         mov	bx, KDATA
  4503 00004DAE 8EDB                <1> 	mov	ds, bx
  4504                              <1> 	;mov	es, bx
  4505 00004DB0 C605[1B5F0100]00    <1> 	MOV     byte [DISK_STATUS1],0
  4506 00004DB7 8A1D[1C5F0100]      <1> 	MOV	BL,[HF_NUM]		; GET NUMBER OF DRIVES
  4507 00004DBD 80E27F              <1> 	AND	DL,7FH			; GET DRIVE NUMBER
  4508 00004DC0 38D3                <1> 	CMP	BL,DL
  4509 00004DC2 763C                <1> 	JBE	short RDT_NOT_PRESENT 	; RETURN DRIVE NOT PRESENT
  4510 00004DC4 0FB6C2              <1> 	movzx	eax, dl ; 28/08/2020
  4511 00004DC7 E8BC040000          <1> 	CALL	GET_VEC 		; GET DISK PARAMETERS ADDRESS
  4512                              <1> 	
  4513                              <1> 	; 28/08/2020 - TRDOS 386 v2
  4514 00004DCC F6431440            <1> 	test	byte [ebx+20], 40h	; LBA bit (bit 6)
  4515 00004DD0 751D                <1> 	jnz	short RDT3 ; LBA disk (may be > 8GB)
  4516                              <1> 
  4517                              <1> 	;MOV	AL,[ES:BX+2]		; HEADS
  4518 00004DD2 8A4302              <1> 	mov	al, [ebx+2]
  4519                              <1> 	;MOV	CL,[ES:BX+14]
  4520 00004DD5 8A4B0E              <1> 	mov	cl, [ebx+14]
  4521 00004DD8 F6E9                <1> 	IMUL	CL			; * NUMBER OF SECTORS
  4522                              <1> 	;MOV	CX,[ES:BX]		; MAX NUMBER OF CYLINDERS
  4523 00004DDA 668B0B              <1> 	mov	cx, [ebx]
  4524                              <1> 	;
  4525                              <1> 	; 02/01/2015 
  4526                              <1> 	; ** leave the last cylinder as reserved for diagnostics **
  4527                              <1> 	; (Also in Award BIOS - 1999, AHDSK.ASM, FUN15 -> sub ax, 1)
  4528 00004DDD 6649                <1> 	DEC	CX			; LEAVE ONE FOR DIAGNOSTICS
  4529                              <1> 	;
  4530 00004DDF 66F7E9              <1> 	IMUL	CX			; NUMBER OF SECTORS
  4531 00004DE2 6689D1              <1> 	MOV	CX,DX			; HIGH ORDER HALF
  4532 00004DE5 6689C2              <1> 	MOV	DX,AX			; LOW ORDER HALF
  4533                              <1> 	;SUB	AX,AX
  4534                              <1> 	; 28/08/2020
  4535                              <1> 	;sub	al, al
  4536                              <1> RDT4:
  4537 00004DE8 29C0                <1> 	sub	eax, eax ; 28/08/2020
  4538                              <1> 	;
  4539 00004DEA B403                <1> 	MOV	AH,03H			; INDICATE FIXED DISK
  4540                              <1> 	; 30/08/2020 (clc is not needed here)
  4541                              <1> 	;and	byte [esp+8], 0FEh ; clear carry bit of eflags register
  4542                              <1> RDT2:	
  4543 00004DEC 5B                  <1> 	POP	eBX			; RESTORE REGISTERS
  4544                              <1> 	;POP	ES
  4545 00004DED 1F                  <1> 	POP	DS
  4546                              <1> 	; (*) CLC			; CLEAR CARRY
  4547                              <1> 	;RETf	2
  4548                              <1> 	; (*) 29/05/2016
  4549                              <1> 	; (*) retf 4
  4550                              <1> 	; 30/08/2020 (clc is not needed here)
  4551                              <1> 	;and	byte [esp+8], 0FEh ; clear carry bit of eflags register
  4552 00004DEE CF                  <1> 	iretd
  4553                              <1> 
  4554                              <1> RDT3:	; 28/08/2020
  4555                              <1> 	; (use the result of INT 13h, function 48h as disk size)
  4556                              <1> 	; eax = al = zero based hard disk number
  4557                              <1> 	; 29/08/2020
  4558                              <1> 	;add	al, 2 ; hd0 = physical disk drive 2
  4559 00004DEF C0E002              <1> 	shl	al, 2 ; * 4
  4560                              <1> RDT5:
  4561                              <1> 	;add	eax, drv.size
  4562 00004DF2 05[E6640000]        <1> 	add	eax, drv.size+8 ; 29/08/2020
  4563 00004DF7 668B10              <1> 	mov	dx, [eax]   ; low word of disk size
  4564 00004DFA 668B4802            <1> 	mov	cx, [eax+2] ; high word of disk size
  4565                              <1> 	;sub	eax, eax
  4566 00004DFE EBE8                <1> 	jmp	short RDT4		
  4567                              <1> 
  4568                              <1> RDT_NOT_PRESENT:
  4569                              <1> 	; 30/08/2020
  4570 00004E00 C605[1B5F0100]AA    <1> 	mov	byte [DISK_STATUS1], NOT_RDY ; DRIVE NOT READY
  4571                              <1> 
  4572                              <1> 	;SUB	AX,AX			; DRIVE NOT PRESENT RETURN
  4573 00004E07 29C0                <1> 	sub	eax, eax ; 30/08/2020
  4574 00004E09 6689C1              <1> 	MOV	CX,AX			; ZERO BLOCK COUNT
  4575 00004E0C 6689C2              <1> 	MOV	DX,AX
  4576                              <1> 	; 30/08/2020
  4577 00004E0F 804C241001          <1> 	or	byte [esp+16], 1 ; set carry bit of eflags register
  4578                              <1> 		; cf = 1 -> ah = 0, drive not ready, disk type = 0
  4579 00004E14 EBD6                <1> 	JMP	short RDT2
  4580                              <1> 
  4581                              <1> ; 28/05/2016
  4582                              <1> ; 27/05/2016 - TRDOS 386 (TRDOS v2.0)
  4583                              <1> 
  4584                              <1> ;----------------------------------------
  4585                              <1> ;	GET PARAMETERS	     (AH = 08H) :
  4586                              <1> ;----------------------------------------
  4587                              <1> 
  4588                              <1> GET_PARM_N:
  4589                              <1> 	; ebx = user's buffer address for parameters table
  4590                              <1> ;GET_PARM:				; GET DRIVE PARAMETERS
  4591 00004E16 1E                  <1> 	PUSH	DS			; SAVE REGISTERS
  4592 00004E17 06                  <1> 	PUSH	ES
  4593 00004E18 53                  <1> 	PUSH	eBX
  4594                              <1> 	;MOV	AX,ABS0 		; ESTABLISH ADDRESSING
  4595                              <1> 	;MOV	DS,AX
  4596                              <1> 	;TEST	DL,1			; CHECK FOR DRIVE 1
  4597                              <1> 	;JZ	short G0
  4598                              <1> 	;LES	BX,@HF1_TBL_VEC
  4599                              <1> 	;JMP	SHORT G1
  4600                              <1> ;G0:	LES	BX,@HF_TBL_VEC
  4601                              <1> ;G1:
  4602                              <1> 	;CALL	DDS			; ESTABLISH SEGMENT
  4603                              <1> 	; 22/12/2014
  4604                              <1> 	;push	cs
  4605                              <1> 	;pop	ds
  4606 00004E19 66BB1000            <1> 	mov	bx, KDATA
  4607 00004E1D 8EDB                <1> 	mov	ds, bx
  4608 00004E1F 8EC3                <1> 	mov	es, bx	; 27/05/2016
  4609                              <1> 	;
  4610 00004E21 80EA80              <1> 	SUB	DL,80H
  4611                              <1> 	;CMP	DL,MAX_FILE		; TEST WITHIN RANGE
  4612                              <1> 	;JAE	short G4 ; 29/08/2020 - BugFix
  4613                              <1> 	; 30/08/2020
  4614 00004E24 3A15[1C5F0100]      <1> 	cmp	dl, [HF_NUM] ; is hard disk index < hard disk count ?	
  4615 00004E2A 736A                <1> 	jae	short G4     ; no, error ! drive not ready !	
  4616                              <1> 	;
  4617 00004E2C 31DB                <1> 	xor	ebx, ebx ; 21/02/2015
  4618                              <1> 	; 22/12/2014
  4619 00004E2E 88D3                <1> 	mov	bl, dl
  4620                              <1> 	;xor	bh, bh  
  4621 00004E30 C0E302              <1> 	shl	bl, 2			; convert index to offset
  4622                              <1> 	;add	bx, HF_TBL_VEC
  4623 00004E33 81C3[205F0100]      <1> 	add	ebx, HF_TBL_VEC
  4624                              <1> 	;mov	ax, [bx+2]
  4625                              <1> 	;mov	es, ax			; dpt segment
  4626                              <1> 	;mov	bx, [bx]		; dpt offset
  4627 00004E39 8B1B                <1> 	mov	ebx, [ebx] ; 32 bit offset	
  4628                              <1> 
  4629 00004E3B C605[1B5F0100]00    <1> 	MOV	byte [DISK_STATUS1],0
  4630                              <1>         ;MOV	AX,[ES:BX]		; MAX NUMBER OF CYLINDERS
  4631 00004E42 668B03              <1> 	mov	ax, [ebx]
  4632                              <1> 	;;SUB	AX,2			; ADJUST FOR 0-N
  4633 00004E45 6648                <1> 	dec	ax			; max. cylinder number
  4634 00004E47 88C5                <1> 	MOV	CH,AL
  4635 00004E49 66250003            <1> 	AND	AX,0300H		; HIGH TWO BITS OF CYLINDER
  4636 00004E4D 66D1E8              <1> 	SHR	AX,1
  4637 00004E50 66D1E8              <1> 	SHR	AX,1
  4638                              <1> 	;OR	AL,[ES:BX+14]		; SECTORS
  4639 00004E53 0A430E              <1> 	or	al, [ebx+14]
  4640 00004E56 88C1                <1> 	MOV	CL,AL
  4641                              <1> 	;MOV	DH,[ES:BX+2]		; HEADS
  4642 00004E58 8A7302              <1> 	mov	dh, [ebx+2]
  4643 00004E5B FECE                <1> 	DEC	DH			; 0-N RANGE
  4644 00004E5D 8A15[1C5F0100]      <1> 	MOV	DL,[HF_NUM]		; DRIVE COUNT
  4645 00004E63 6629C0              <1> 	SUB	AX,AX
  4646                              <1>         ;27/12/2014 
  4647                              <1> 	;mov	di, bx			; HDPT offset
  4648                              <1> 
  4649                              <1> 	; 29/08/2020
  4650 00004E66 833C2400            <1> 	cmp	dword [esp], 0
  4651 00004E6A 7703                <1> 	ja	short G7 ; ebx > 0
  4652                              <1> 
  4653                              <1> 	; if EBX (user's buffer address) = 0, do not copy DPT
  4654 00004E6C 5B                  <1> 	pop	ebx
  4655 00004E6D EB24                <1> 	jmp	short G5
  4656                              <1> G7:
  4657                              <1> 	; 27/05/2016
  4658                              <1> 	; return fixed disk parameters table to user
  4659                              <1> 	; in user's buffer, which is pointed by EBX
  4660                              <1> 	;
  4661 00004E6F 873C24              <1> 	xchg	edi, [esp]		; ebx (input)-> edi, edi -> [esp]
  4662 00004E72 56                  <1> 	push	esi
  4663 00004E73 89DE                <1> 	mov	esi, ebx		; hard disk parameter table (32 bytes)	
  4664 00004E75 89FB                <1> 	mov	ebx, edi		; ebx = user's buffer address
  4665 00004E77 51                  <1> 	push	ecx
  4666 00004E78 50                  <1> 	push	eax
  4667 00004E79 B920000000          <1> 	mov	ecx, 32 ; 32 bytes
  4668 00004E7E E8DF9E0000          <1> 	call	transfer_to_user_buffer ; trdosk6.s (16/05/2016)
  4669 00004E83 58                  <1> 	pop	eax
  4670 00004E84 59                  <1> 	pop	ecx
  4671 00004E85 5E                  <1> 	pop	esi
  4672 00004E86 5F                  <1> 	pop	edi
  4673 00004E87 730A                <1> 	jnc	short G5
  4674                              <1> 	; 29/05/2016 (*)
  4675 00004E89 B8FF000000          <1> 	mov	eax, 0FFh ; unknown error !
  4676                              <1> G6:
  4677 00004E8E 804C241001          <1> 	or	byte [esp+16], 1 ; set carry bit of eflags register
  4678                              <1> G5:
  4679                              <1> 	; 27/05/2016
  4680                              <1> 	;POP	eBX			; RESTORE REGISTERS
  4681 00004E93 07                  <1> 	POP	ES
  4682 00004E94 1F                  <1> 	POP	DS
  4683                              <1> 	;RETf	2
  4684                              <1> 	; (*) 29/05/2016
  4685                              <1> 	; (*) retf 4
  4686                              <1> 	; (*) or byte [esp+8], 1 ; set carry bit of eflags register
  4687 00004E95 CF                  <1> 	iretd
  4688                              <1> G4:
  4689 00004E96 C605[1B5F0100]07    <1> 	MOV     byte [DISK_STATUS1],INIT_FAIL ; OPERATION FAILED
  4690                              <1> 	;mov	ah, NOT_DRY ; 30/08/2020 - 'drive not ready' error code
  4691 00004E9D B407                <1> 	MOV	AH,INIT_FAIL
  4692 00004E9F 28C0                <1> 	SUB	AL,AL
  4693                              <1> 	;SUB	DX,DX
  4694                              <1> 	; 30/08/2020
  4695 00004EA1 8A15[1C5F0100]      <1> 	mov	dl, [HF_NUM] ; disk count
  4696 00004EA7 28F6                <1> 	sub	dh, dh
  4697 00004EA9 6629C9              <1> 	SUB	CX,CX
  4698                              <1> 	; 29/05/2016 (*)
  4699                              <1> 	;STC				; SET ERROR FLAG
  4700                              <1> 	;JMP	short G5
  4701                              <1> 	; 29/08/2020 - BugFix
  4702 00004EAC 5B                  <1> 	pop	ebx
  4703 00004EAD EBDF                <1> 	jmp	short G6
  4704                              <1> 
  4705                              <1> ;----------------------------------------
  4706                              <1> ;	INITIALIZE DRIVE     (AH = 09H) :
  4707                              <1> ;----------------------------------------
  4708                              <1> 	; 03/01/2015
  4709                              <1> 	; According to ATA-ATAPI specification v2.0 to v5.0
  4710                              <1> 	; logical sector per logical track
  4711                              <1> 	; and logical heads - 1 would be set but
  4712                              <1> 	; it is seen as it will be good
  4713                              <1> 	; if physical parameters will be set here
  4714                              <1> 	; because, number of heads <= 16.
  4715                              <1> 	; (logical heads usually more than 16)
  4716                              <1> 	; NOTE: ATA logical parameters (software C, H, S)
  4717                              <1> 	;	== INT 13h physical parameters
  4718                              <1> 
  4719                              <1> ;INIT_DRV:
  4720                              <1> ;	MOV	byte [CMD_BLOCK+6],SET_PARM_CMD
  4721                              <1> ;	CALL	GET_VEC 		; ES:BX -> PARAMETER BLOCK
  4722                              <1> ;	MOV	AL,[ES:BX+2]		; GET NUMBER OF HEADS
  4723                              <1> ;	DEC	AL			; CONVERT TO 0-INDEX
  4724                              <1> ;	MOV	AH,[CMD_BLOCK+5] 	; GET SDH REGISTER
  4725                              <1> ;	AND	AH,0F0H 		; CHANGE HEAD NUMBER
  4726                              <1> ;	OR	AH,AL			; TO MAX HEAD
  4727                              <1> ;	MOV	[CMD_BLOCK+5],AH
  4728                              <1> ;	MOV	AL,[ES:BX+14]		; MAX SECTOR NUMBER
  4729                              <1> ;	MOV	[CMD_BLOCK+1],AL
  4730                              <1> ;	SUB	AX,AX
  4731                              <1> ;	MOV	[CMD_BLOCK+3],AL 	; ZERO FLAGS
  4732                              <1> ;	CALL	COMMAND 		; TELL CONTROLLER
  4733                              <1> ;	JNZ	short INIT_EXIT		; CONTROLLER BUSY ERROR
  4734                              <1> ;	CALL	NOT_BUSY		; WAIT FOR IT TO BE DONE
  4735                              <1> ;	JNZ	short INIT_EXIT		; TIME OUT
  4736                              <1> ;	CALL	CHECK_STATUS
  4737                              <1> ;INIT_EXIT:
  4738                              <1> ;	RETn
  4739                              <1> 
  4740                              <1> ; 04/01/2015
  4741                              <1> ; 02/01/2015 - Derived from from AWARD BIOS 1999
  4742                              <1> ;				 AHDSK.ASM - INIT_DRIVE
  4743                              <1> INIT_DRV:
  4744                              <1> 	;xor	ah,ah
  4745 00004EAF 31C0                <1> 	xor	eax, eax ; 21/02/2015
  4746 00004EB1 B00B                <1> 	mov	al,11 ; Physical heads from translated HDPT
  4747 00004EB3 3825[305F0100]      <1>         cmp     [LBAMode], ah   ; 0
  4748 00004EB9 7702                <1> 	ja	short idrv0
  4749 00004EBB B002                <1> 	mov	al,2  ; Physical heads from standard HDPT
  4750                              <1> idrv0:
  4751                              <1> 	; DL = drive number (0 based)
  4752 00004EBD E8C6030000          <1> 	call	GET_VEC
  4753                              <1> 	;push	bx
  4754 00004EC2 53                  <1> 	push	ebx ; 21/02/2015
  4755                              <1> 	;add	bx,ax
  4756 00004EC3 01C3                <1> 	add	ebx, eax
  4757                              <1> 	;; 05/01/2015
  4758 00004EC5 8A25[A4640000]      <1> 	mov	ah, [hf_m_s] ; drive number (0= master, 1= slave)
  4759                              <1> 	;;and 	ah,1 
  4760 00004ECB C0E404              <1> 	shl	ah,4
  4761 00004ECE 80CCA0              <1> 	or	ah,0A0h  ; Drive/Head register - 10100000b (A0h)	
  4762                              <1> 	;mov	al,[es:bx]
  4763 00004ED1 8A03                <1> 	mov	al, [ebx] ; 21/02/2015
  4764 00004ED3 FEC8                <1> 	dec	al	 ; last head number 
  4765                              <1> 	;and	al,0Fh
  4766 00004ED5 08E0                <1> 	or	al,ah	 ; lower 4 bits for head number
  4767                              <1> 	;
  4768 00004ED7 C645FE91            <1> 	mov	byte [CMD_BLOCK+6],SET_PARM_CMD
  4769 00004EDB 8845FD              <1> 	mov	[CMD_BLOCK+5],al
  4770                              <1> 	;pop	bx
  4771 00004EDE 5B                  <1> 	pop	ebx
  4772 00004EDF 29C0                <1> 	sub	eax, eax ; 21/02/2015
  4773 00004EE1 B004                <1> 	mov	al,4 ; Physical sec per track from translated HDPT
  4774 00004EE3 803D[305F0100]00    <1> 	cmp	byte [LBAMode], 0
  4775 00004EEA 7702                <1> 	ja	short idrv1
  4776 00004EEC B00E                <1> 	mov	al,14 ; Physical sec per track from standard HDPT
  4777                              <1> idrv1:
  4778                              <1> 	;xor	ah,ah
  4779                              <1> 	;add	bx,ax
  4780 00004EEE 01C3                <1> 	add	ebx, eax ; 21/02/2015
  4781                              <1> 	;mov	al,[es:bx]
  4782                              <1> 			; sector number
  4783 00004EF0 8A03                <1> 	mov	al, [ebx]
  4784 00004EF2 8845F9              <1> 	mov	[CMD_BLOCK+1],al
  4785 00004EF5 28C0                <1> 	sub	al,al
  4786 00004EF7 8845FB              <1> 	mov	[CMD_BLOCK+3],al  ; ZERO FLAGS
  4787 00004EFA E8CA010000          <1> 	call	COMMAND 	  ; TELL CONTROLLER
  4788 00004EFF 750C                <1> 	jnz	short INIT_EXIT	  ; CONTROLLER BUSY ERROR
  4789 00004F01 E878020000          <1> 	call	NOT_BUSY	  ; WAIT FOR IT TO BE DONE
  4790 00004F06 7505                <1> 	jnz	short INIT_EXIT	  ; TIME OUT
  4791 00004F08 E8C9020000          <1> 	call	CHECK_STATUS
  4792                              <1> INIT_EXIT:
  4793 00004F0D C3                  <1> 	RETn
  4794                              <1> 
  4795                              <1> ;----------------------------------------
  4796                              <1> ;	READ LONG	     (AH = 0AH) :
  4797                              <1> ;----------------------------------------
  4798                              <1> 
  4799                              <1> RD_LONG:
  4800                              <1> 	;MOV	@CMD_BLOCK+6,READ_CMD OR ECC_MODE
  4801 00004F0E C645FE22            <1>         mov     byte [CMD_BLOCK+6],READ_CMD + ECC_MODE 
  4802 00004F12 E9E0000000          <1>         JMP     COMMANDI
  4803                              <1> 
  4804                              <1> ;----------------------------------------
  4805                              <1> ;	WRITE LONG	     (AH = 0BH) :
  4806                              <1> ;----------------------------------------
  4807                              <1> 
  4808                              <1> WR_LONG:
  4809                              <1> 	;MOV	@CMD_BLOCK+6,WRITE_CMD OR ECC_MODE
  4810 00004F17 C645FE32            <1>         MOV     byte [CMD_BLOCK+6],WRITE_CMD + ECC_MODE
  4811 00004F1B E932010000          <1>         JMP     COMMANDO
  4812                              <1> 
  4813                              <1> ;----------------------------------------
  4814                              <1> ;	SEEK		     (AH = 0CH) :
  4815                              <1> ;----------------------------------------
  4816                              <1> 
  4817                              <1> DISK_SEEK:
  4818 00004F20 C645FE70            <1>         MOV     byte [CMD_BLOCK+6],SEEK_CMD
  4819 00004F24 E8A0010000          <1> 	CALL	COMMAND
  4820 00004F29 751C                <1> 	JNZ	short DS_EXIT 		; CONTROLLER BUSY ERROR
  4821 00004F2B E812020000          <1> 	CALL	_WAIT
  4822 00004F30 7515                <1>         JNZ     DS_EXIT                 ; TIME OUT ON SEEK
  4823 00004F32 E89F020000          <1> 	CALL	CHECK_STATUS
  4824 00004F37 803D[1B5F0100]40    <1>         CMP     byte [DISK_STATUS1],BAD_SEEK
  4825 00004F3E 7507                <1> 	JNE	short DS_EXIT
  4826 00004F40 C605[1B5F0100]00    <1>         MOV     byte [DISK_STATUS1],0
  4827                              <1> DS_EXIT:
  4828 00004F47 C3                  <1> 	RETn
  4829                              <1> 
  4830                              <1> ;----------------------------------------
  4831                              <1> ;	TEST DISK READY      (AH = 10H) :
  4832                              <1> ;----------------------------------------
  4833                              <1> 
  4834                              <1> TST_RDY:				; WAIT FOR CONTROLLER
  4835 00004F48 E831020000          <1> 	CALL	NOT_BUSY
  4836 00004F4D 751C                <1> 	JNZ	short TR_EX
  4837 00004F4F 8A45FD              <1> 	MOV	AL,[CMD_BLOCK+5] 	; SELECT DRIVE
  4838 00004F52 668B15[A0640000]    <1> 	MOV	DX,[HF_PORT]
  4839 00004F59 80C206              <1> 	add	dl,6
  4840 00004F5C EE                  <1> 	OUT	DX,AL
  4841 00004F5D E88C020000          <1> 	CALL	CHECK_ST		; CHECK STATUS ONLY
  4842 00004F62 7507                <1> 	JNZ	short TR_EX
  4843 00004F64 C605[1B5F0100]00    <1> 	MOV	byte [DISK_STATUS1],0 	; WIPE OUT DATA CORRECTED ERROR
  4844                              <1> TR_EX:	
  4845 00004F6B C3                  <1> 	RETn
  4846                              <1> 
  4847                              <1> ;----------------------------------------
  4848                              <1> ;	RECALIBRATE	     (AH = 11H) :
  4849                              <1> ;----------------------------------------
  4850                              <1> 
  4851                              <1> HDISK_RECAL:
  4852 00004F6C C645FE10            <1>         MOV     byte [CMD_BLOCK+6],RECAL_CMD ; 10h, 16
  4853 00004F70 E854010000          <1> 	CALL	COMMAND 		; START THE OPERATION
  4854 00004F75 7523                <1> 	JNZ	short RECAL_EXIT	; ERROR
  4855 00004F77 E8C6010000          <1> 	CALL	_WAIT			; WAIT FOR COMPLETION
  4856 00004F7C 7407                <1> 	JZ	short RECAL_X 		; TIME OUT ONE OK ?
  4857 00004F7E E8BF010000          <1> 	CALL	_WAIT			; WAIT FOR COMPLETION LONGER
  4858 00004F83 7515                <1> 	JNZ	short RECAL_EXIT	; TIME OUT TWO TIMES IS ERROR
  4859                              <1> RECAL_X:
  4860 00004F85 E84C020000          <1> 	CALL	CHECK_STATUS
  4861 00004F8A 803D[1B5F0100]40    <1> 	CMP	byte [DISK_STATUS1],BAD_SEEK ; SEEK NOT COMPLETE
  4862 00004F91 7507                <1> 	JNE	short RECAL_EXIT	; IS OK
  4863 00004F93 C605[1B5F0100]00    <1> 	MOV	byte [DISK_STATUS1],0
  4864                              <1> RECAL_EXIT:
  4865 00004F9A 803D[1B5F0100]00    <1>         CMP     byte [DISK_STATUS1],0
  4866 00004FA1 C3                  <1> 	RETn
  4867                              <1> 
  4868                              <1> ;----------------------------------------
  4869                              <1> ;      CONTROLLER DIAGNOSTIC (AH = 14H) :
  4870                              <1> ;----------------------------------------
  4871                              <1> 
  4872                              <1> CTLR_DIAGNOSTIC:
  4873 00004FA2 FA                  <1>         CLI                             ; DISABLE INTERRUPTS WHILE CHANGING MASK
  4874 00004FA3 E4A1                <1> 	IN	AL,INTB01		; TURN ON SECOND INTERRUPT CHIP
  4875                              <1> 	;AND	AL,0BFH
  4876 00004FA5 243F                <1> 	and	al, 3Fh			; enable IRQ 14 & IRQ 15
  4877                              <1> 	;JMP	$+2
  4878                              <1> 	IODELAY
  4878 00004FA7 EB00                <2>  jmp short $+2
  4878 00004FA9 EB00                <2>  jmp short $+2
  4879 00004FAB E6A1                <1> 	OUT	INTB01,AL
  4880                              <1> 	IODELAY
  4880 00004FAD EB00                <2>  jmp short $+2
  4880 00004FAF EB00                <2>  jmp short $+2
  4881 00004FB1 E421                <1> 	IN	AL,INTA01		; LET INTERRUPTS PASS THRU TO
  4882 00004FB3 24FB                <1> 	AND	AL,0FBH 		;  SECOND CHIP
  4883                              <1> 	;JMP	$+2
  4884                              <1> 	IODELAY
  4884 00004FB5 EB00                <2>  jmp short $+2
  4884 00004FB7 EB00                <2>  jmp short $+2
  4885 00004FB9 E621                <1> 	OUT	INTA01,AL
  4886 00004FBB FB                  <1> 	STI
  4887 00004FBC E8BD010000          <1> 	CALL	NOT_BUSY		; WAIT FOR CARD
  4888 00004FC1 752B                <1> 	JNZ	short CD_ERR		; BAD CARD
  4889                              <1> 	;MOV	DX, HF_PORT+7
  4890 00004FC3 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  4891 00004FCA 80C207              <1> 	add	dl, 7
  4892 00004FCD B090                <1> 	MOV	AL,DIAG_CMD		; START DIAGNOSE
  4893 00004FCF EE                  <1> 	OUT	DX,AL
  4894 00004FD0 E8A9010000          <1> 	CALL	NOT_BUSY		; WAIT FOR IT TO COMPLETE
  4895 00004FD5 B480                <1> 	MOV	AH,TIME_OUT
  4896 00004FD7 7517                <1> 	JNZ	short CD_EXIT 		; TIME OUT ON DIAGNOSTIC
  4897                              <1> 	;MOV	DX,HF_PORT+1		; GET ERROR REGISTER
  4898 00004FD9 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  4899 00004FE0 FEC2                <1> 	inc	dl
  4900 00004FE2 EC                  <1> 	IN	AL,DX
  4901 00004FE3 A2[125F0100]        <1> 	MOV	[HF_ERROR],AL		; SAVE IT
  4902 00004FE8 B400                <1> 	MOV	AH,0
  4903 00004FEA 3C01                <1> 	CMP	AL,1			; CHECK FOR ALL OK
  4904 00004FEC 7402                <1> 	JE	SHORT CD_EXIT
  4905 00004FEE B420                <1> CD_ERR: MOV	AH,BAD_CNTLR
  4906                              <1> CD_EXIT:
  4907 00004FF0 8825[1B5F0100]      <1> 	MOV	[DISK_STATUS1],AH
  4908 00004FF6 C3                  <1> 	RETn
  4909                              <1> 
  4910                              <1> ;----------------------------------------
  4911                              <1> ; COMMANDI				:
  4912                              <1> ;	REPEATEDLY INPUTS DATA TILL	:
  4913                              <1> ;	NSECTOR RETURNS ZERO		:
  4914                              <1> ;----------------------------------------
  4915                              <1> COMMANDI:
  4916 00004FF7 E862020000          <1> 	CALL	CHECK_DMA		; CHECK 64K BOUNDARY ERROR
  4917 00004FFC 7253                <1> 	JC	short CMD_ABORT
  4918                              <1> 	;MOV	DI,BX
  4919 00004FFE 89DF                <1> 	mov	edi, ebx ; 21/02/2015
  4920 00005000 E8C4000000          <1> 	CALL	COMMAND 		; OUTPUT COMMAND
  4921 00005005 754A                <1> 	JNZ	short CMD_ABORT
  4922                              <1> CMD_I1:
  4923 00005007 E836010000          <1> 	CALL	_WAIT			; WAIT FOR DATA REQUEST INTERRUPT
  4924 0000500C 7543                <1> 	JNZ	short TM_OUT		; TIME OUT
  4925                              <1> cmd_i1x: ; 18/02/2016
  4926                              <1> 	;MOV	CX,256			; SECTOR SIZE IN WORDS
  4927 0000500E B900010000          <1> 	mov	ecx, 256 ; 21/02/2015	
  4928                              <1> 	;MOV	DX,HF_PORT
  4929 00005013 668B15[A0640000]    <1> 	mov	dx,[HF_PORT]
  4930 0000501A FA                  <1> 	CLI
  4931 0000501B FC                  <1> 	CLD
  4932 0000501C F3666D              <1> 	REP	INSW			; GET THE SECTOR
  4933 0000501F FB                  <1> 	STI
  4934 00005020 F645FE02            <1> 	TEST	byte [CMD_BLOCK+6],ECC_MODE ; CHECK FOR NORMAL INPUT
  4935 00005024 7419                <1> 	JZ	short CMD_I3
  4936 00005026 E880010000          <1> 	CALL	WAIT_DRQ		; WAIT FOR DATA REQUEST
  4937 0000502B 7224                <1> 	JC	short TM_OUT
  4938                              <1> 	;MOV	DX,HF_PORT
  4939 0000502D 668B15[A0640000]    <1> 	mov	dx,[HF_PORT]
  4940                              <1> 	;MOV	CX,4			; GET ECC BYTES
  4941 00005034 B904000000          <1> 	mov 	ecx, 4 ; mov cx, 4 
  4942 00005039 EC                  <1> CMD_I2: IN	AL,DX
  4943                              <1> 	;MOV	[ES:DI],AL		; GO SLOW FOR BOARD
  4944 0000503A 8807                <1> 	mov 	[edi], al ; 21/02/2015
  4945 0000503C 47                  <1> 	INC	eDI
  4946 0000503D E2FA                <1> 	LOOP	CMD_I2
  4947                              <1> CMD_I3: 
  4948                              <1> 	; wait for 400 ns
  4949 0000503F 80C207              <1> 	add 	dl, 7
  4950 00005042 EC                  <1> 	in	al, dx
  4951 00005043 EC                  <1> 	in	al, dx
  4952 00005044 EC                  <1> 	in	al, dx
  4953                              <1> 	;
  4954 00005045 E88C010000          <1> 	CALL	CHECK_STATUS
  4955 0000504A 7505                <1> 	JNZ	short CMD_ABORT		; ERROR RETURNED
  4956 0000504C FE4DF9              <1> 	DEC	byte [CMD_BLOCK+1]	; CHECK FOR MORE
  4957                              <1> 	;JNZ	SHORT CMD_I1
  4958 0000504F 75BD                <1> 	jnz	short cmd_i1x ; 18/02/2016
  4959                              <1> CMD_ABORT:
  4960 00005051 C3                  <1> TM_OUT: RETn
  4961                              <1> 
  4962                              <1> ;----------------------------------------
  4963                              <1> ; COMMANDO				:
  4964                              <1> ;	REPEATEDLY OUTPUTS DATA TILL	:
  4965                              <1> ;	NSECTOR RETURNS ZERO		:
  4966                              <1> ;----------------------------------------
  4967                              <1> COMMANDO:
  4968 00005052 E807020000          <1> 	CALL	CHECK_DMA		; CHECK 64K BOUNDARY ERROR
  4969 00005057 72F8                <1> 	JC	short CMD_ABORT
  4970 00005059 89DE                <1> CMD_OF: MOV	eSI,eBX ; 21/02/2015
  4971 0000505B E869000000          <1> 	CALL	COMMAND 		; OUTPUT COMMAND
  4972 00005060 75EF                <1> 	JNZ	short CMD_ABORT
  4973 00005062 E844010000          <1> 	CALL	WAIT_DRQ		; WAIT FOR DATA REQUEST
  4974 00005067 72E8                <1> 	JC	short TM_OUT			; TOO LONG
  4975                              <1> CMD_O1: ;PUSH	DS
  4976                              <1> 	;PUSH	ES			; MOVE ES TO DS
  4977                              <1> 	;POP	DS
  4978                              <1> 	;MOV	CX,256			; PUT THE DATA OUT TO THE CARD
  4979                              <1> 	;MOV	DX,HF_PORT
  4980                              <1> 	; 01/02/2015
  4981 00005069 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  4982                              <1> 	;push	es
  4983                              <1> 	;pop	ds
  4984                              <1> 	;mov	cx, 256
  4985 00005070 B900010000          <1> 	mov	ecx, 256 ; 21/02/2015
  4986 00005075 FA                  <1> 	CLI
  4987 00005076 FC                  <1> 	CLD
  4988 00005077 F3666F              <1> 	REP	OUTSW
  4989 0000507A FB                  <1> 	STI
  4990                              <1> 	;POP	DS			; RESTORE DS
  4991 0000507B F645FE02            <1> 	TEST	byte [CMD_BLOCK+6],ECC_MODE ; CHECK FOR NORMAL OUTPUT
  4992 0000507F 7419                <1> 	JZ	short CMD_O3
  4993 00005081 E825010000          <1> 	CALL	WAIT_DRQ		; WAIT FOR DATA REQUEST
  4994 00005086 72C9                <1> 	JC	short TM_OUT
  4995                              <1> 	;MOV	DX,HF_PORT
  4996 00005088 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  4997                              <1> 	;MOV	CX,4			; OUTPUT THE ECC BYTES
  4998 0000508F B904000000          <1> 	mov	ecx, 4  ; mov cx, 4
  4999                              <1> CMD_O2: ;MOV	AL,[ES:SI]
  5000 00005094 8A06                <1> 	mov	al, [esi]
  5001 00005096 EE                  <1> 	OUT	DX,AL
  5002 00005097 46                  <1> 	INC	eSI
  5003 00005098 E2FA                <1> 	LOOP	CMD_O2
  5004                              <1> CMD_O3:
  5005 0000509A E8A3000000          <1> 	CALL	_WAIT			; WAIT FOR SECTOR COMPLETE INTERRUPT
  5006 0000509F 75B0                <1> 	JNZ	short TM_OUT		; ERROR RETURNED
  5007 000050A1 E830010000          <1> 	CALL	CHECK_STATUS
  5008 000050A6 75A9                <1> 	JNZ	short CMD_ABORT
  5009 000050A8 F605[115F0100]08    <1> 	TEST	byte [HF_STATUS],ST_DRQ	; CHECK FOR MORE
  5010 000050AF 75B8                <1> 	JNZ	SHORT CMD_O1
  5011                              <1> 	;MOV	DX,HF_PORT+2		; CHECK RESIDUAL SECTOR COUNT
  5012 000050B1 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  5013                              <1> 	;add	dl, 2
  5014 000050B8 FEC2                <1> 	inc	dl
  5015 000050BA FEC2                <1> 	inc	dl
  5016 000050BC EC                  <1> 	IN	AL,DX			;
  5017 000050BD A8FF                <1> 	TEST	AL,0FFH 		;
  5018 000050BF 7407                <1> 	JZ	short CMD_O4			; COUNT = 0  OK
  5019 000050C1 C605[1B5F0100]BB    <1> 	MOV	byte [DISK_STATUS1],UNDEF_ERR 
  5020                              <1> 					; OPERATION ABORTED - PARTIAL TRANSFER
  5021                              <1> CMD_O4:
  5022 000050C8 C3                  <1> 	RETn
  5023                              <1> 
  5024                              <1> ;--------------------------------------------------------
  5025                              <1> ; COMMAND						:
  5026                              <1> ;	THIS ROUTINE OUTPUTS THE COMMAND BLOCK		:
  5027                              <1> ; OUTPUT						:
  5028                              <1> ;	BL = STATUS					:
  5029                              <1> ;	BH = ERROR REGISTER				:
  5030                              <1> ;--------------------------------------------------------
  5031                              <1> 
  5032                              <1> COMMAND:
  5033 000050C9 53                  <1> 	PUSH	eBX			; WAIT FOR SEEK COMPLETE AND READY
  5034                              <1> 	;;MOV	CX,DELAY_2		; SET INITIAL DELAY BEFORE TEST
  5035                              <1> COMMAND1:
  5036                              <1> 	;;PUSH	CX			; SAVE LOOP COUNT
  5037 000050CA E879FEFFFF          <1> 	CALL	TST_RDY 		; CHECK DRIVE READY
  5038                              <1> 	;;POP	CX
  5039 000050CF 7419                <1> 	JZ	short COMMAND2		; DRIVE IS READY
  5040 000050D1 803D[1B5F0100]80    <1>         CMP     byte [DISK_STATUS1],TIME_OUT ; TST_RDY TIMED OUT--GIVE UP
  5041                              <1> 	;JZ	short CMD_TIMEOUT
  5042                              <1> 	;;LOOP	COMMAND1		; KEEP TRYING FOR A WHILE
  5043                              <1> 	;JMP	SHORT COMMAND4		; ITS NOT GOING TO GET READY
  5044 000050D8 7507                <1> 	jne	short COMMAND4
  5045                              <1> CMD_TIMEOUT:
  5046 000050DA C605[1B5F0100]20    <1> 	MOV	byte [DISK_STATUS1],BAD_CNTLR
  5047                              <1> COMMAND4:
  5048 000050E1 5B                  <1> 	POP	eBX
  5049 000050E2 803D[1B5F0100]00    <1>         CMP     byte [DISK_STATUS1],0   ; SET CONDITION CODE FOR CALLER
  5050 000050E9 C3                  <1> 	RETn
  5051                              <1> COMMAND2:
  5052 000050EA 5B                  <1> 	POP	eBX
  5053 000050EB 57                  <1> 	PUSH	eDI
  5054 000050EC C605[135F0100]00    <1> 	MOV	byte [HF_INT_FLAG],0	; RESET INTERRUPT FLAG
  5055 000050F3 FA                  <1> 	CLI				; INHIBIT INTERRUPTS WHILE CHANGING MASK
  5056 000050F4 E4A1                <1> 	IN	AL,INTB01		; TURN ON SECOND INTERRUPT CHIP
  5057                              <1> 	;AND	AL,0BFH
  5058 000050F6 243F                <1> 	and	al, 3Fh			; Enable IRQ 14 & 15
  5059                              <1> 	;JMP	$+2
  5060                              <1> 	IODELAY
  5060 000050F8 EB00                <2>  jmp short $+2
  5060 000050FA EB00                <2>  jmp short $+2
  5061 000050FC E6A1                <1> 	OUT	INTB01,AL
  5062 000050FE E421                <1> 	IN	AL,INTA01		; LET INTERRUPTS PASS THRU TO
  5063 00005100 24FB                <1> 	AND	AL,0FBH 		;  SECOND CHIP
  5064                              <1> 	;JMP	$+2
  5065                              <1> 	IODELAY
  5065 00005102 EB00                <2>  jmp short $+2
  5065 00005104 EB00                <2>  jmp short $+2
  5066 00005106 E621                <1> 	OUT	INTA01,AL
  5067 00005108 FB                  <1> 	STI
  5068 00005109 31FF                <1> 	XOR	eDI,eDI			; INDEX THE COMMAND TABLE
  5069                              <1> 	;MOV	DX,HF_PORT+1		; DISK ADDRESS
  5070 0000510B 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  5071 00005112 FEC2                <1> 	inc	dl
  5072 00005114 F605[1D5F0100]C0    <1> 	TEST	byte [CONTROL_BYTE],0C0H ; CHECK FOR RETRY SUPPRESSION
  5073 0000511B 7411                <1> 	JZ	short COMMAND3
  5074 0000511D 8A45FE              <1> 	MOV	AL, [CMD_BLOCK+6] 	; YES-GET OPERATION CODE
  5075 00005120 24F0                <1> 	AND	AL,0F0H 		; GET RID OF MODIFIERS
  5076 00005122 3C20                <1> 	CMP	AL,20H			; 20H-40H IS READ, WRITE, VERIFY
  5077 00005124 7208                <1> 	JB	short COMMAND3
  5078 00005126 3C40                <1> 	CMP	AL,40H
  5079 00005128 7704                <1> 	JA	short COMMAND3
  5080 0000512A 804DFE01            <1> 	OR	byte [CMD_BLOCK+6],NO_RETRIES 
  5081                              <1> 					; VALID OPERATION FOR RETRY SUPPRESS
  5082                              <1> COMMAND3:
  5083 0000512E 8A443DF8            <1> 	MOV	AL,[CMD_BLOCK+eDI]	; GET THE COMMAND STRING BYTE
  5084 00005132 EE                  <1> 	OUT	DX,AL			; GIVE IT TO CONTROLLER
  5085                              <1> 	IODELAY
  5085 00005133 EB00                <2>  jmp short $+2
  5085 00005135 EB00                <2>  jmp short $+2
  5086 00005137 47                  <1> 	INC	eDI			; NEXT BYTE IN COMMAND BLOCK
  5087 00005138 6642                <1> 	INC	DX			; NEXT DISK ADAPTER REGISTER
  5088 0000513A 6683FF07            <1> 	cmp	di, 7	; 1/1/2015	; ALL DONE?
  5089 0000513E 75EE                <1> 	JNZ	short COMMAND3		; NO--GO DO NEXT ONE
  5090 00005140 5F                  <1> 	POP	eDI
  5091 00005141 C3                  <1> 	RETn				; ZERO FLAG IS SET
  5092                              <1> 
  5093                              <1> ;CMD_TIMEOUT:
  5094                              <1> ;	MOV	byte [DISK_STATUS1],BAD_CNTLR
  5095                              <1> ;COMMAND4:
  5096                              <1> ;	POP	BX
  5097                              <1> ;	CMP	[DISK_STATUS1],0 	; SET CONDITION CODE FOR CALLER
  5098                              <1> ;	RETn
  5099                              <1> 
  5100                              <1> ;----------------------------------------
  5101                              <1> ;	WAIT FOR INTERRUPT		:
  5102                              <1> ;----------------------------------------
  5103                              <1> ;WAIT:
  5104                              <1> _WAIT:
  5105 00005142 FB                  <1> 	STI				; MAKE SURE INTERRUPTS ARE ON
  5106                              <1> 	;SUB	CX,CX			; SET INITIAL DELAY BEFORE TEST
  5107                              <1> 	;CLC
  5108                              <1> 	;MOV	AX,9000H		; DEVICE WAIT INTERRUPT
  5109                              <1> 	;INT	15H
  5110                              <1> 	;JC	WT2			; DEVICE TIMED OUT
  5111                              <1> 	;MOV	BL,DELAY_1		; SET DELAY COUNT
  5112                              <1> 
  5113                              <1> 	;mov	bl, WAIT_HDU_INT_HI
  5114                              <1> 	;; 21/02/2015
  5115                              <1> 	;;mov	bl, WAIT_HDU_INT_HI + 1
  5116                              <1> 	;;mov	cx, WAIT_HDU_INT_LO
  5117 00005143 B915160500          <1> 	mov	ecx, WAIT_HDU_INT_LH
  5118                              <1> 					; (AWARD BIOS -> WAIT_FOR_MEM)
  5119                              <1> ;-----	WAIT LOOP
  5120                              <1> 
  5121                              <1> WT1:	
  5122                              <1> 	;TEST	byte [HF_INT_FLAG],80H	; TEST FOR INTERRUPT
  5123 00005148 F605[135F0100]C0    <1> 	test 	byte [HF_INT_FLAG],0C0h
  5124                              <1> 	;LOOPZ	WT1
  5125 0000514F 7517                <1> 	JNZ	short WT3		; INTERRUPT--LETS GO
  5126                              <1> 	;DEC	BL
  5127                              <1> 	;JNZ	short WT1		; KEEP TRYING FOR A WHILE
  5128                              <1> 
  5129                              <1> WT1_hi:
  5130 00005151 E461                <1> 	in	al, SYS1 ; 61h (PORT_B)	; wait for lo to hi
  5131 00005153 A810                <1> 	test	al, 10h			; transition on memory
  5132 00005155 75FA                <1> 	jnz	short WT1_hi		; refresh.
  5133                              <1> WT1_lo:
  5134 00005157 E461                <1> 	in	al, SYS1 		; 061h (PORT_B)	
  5135 00005159 A810                <1> 	test	al, 10h			
  5136 0000515B 74FA                <1> 	jz	short WT1_lo
  5137 0000515D E2E9                <1> 	loop	WT1
  5138                              <1> 	;;or	bl, bl
  5139                              <1> 	;;jz	short WT2	
  5140                              <1> 	;;dec	bl
  5141                              <1> 	;;jmp	short WT1
  5142                              <1> 	;dec	bl
  5143                              <1> 	;jnz	short WT1	
  5144                              <1> 
  5145 0000515F C605[1B5F0100]80    <1> WT2:	MOV	byte [DISK_STATUS1],TIME_OUT ; REPORT TIME OUT ERROR
  5146 00005166 EB0E                <1> 	JMP	SHORT WT4
  5147 00005168 C605[1B5F0100]00    <1> WT3:	MOV	byte [DISK_STATUS1],0
  5148 0000516F C605[135F0100]00    <1> 	MOV	byte [HF_INT_FLAG],0
  5149 00005176 803D[1B5F0100]00    <1> WT4:	CMP	byte [DISK_STATUS1],0 	; SET CONDITION CODE FOR CALLER
  5150 0000517D C3                  <1> 	RETn
  5151                              <1> 
  5152                              <1> ;----------------------------------------
  5153                              <1> ;	WAIT FOR CONTROLLER NOT BUSY	:
  5154                              <1> ;----------------------------------------
  5155                              <1> NOT_BUSY:
  5156 0000517E FB                  <1> 	STI				; MAKE SURE INTERRUPTS ARE ON
  5157                              <1> 	;PUSH	eBX
  5158                              <1> 	;SUB	CX,CX			; SET INITIAL DELAY BEFORE TEST
  5159 0000517F 668B15[A0640000]    <1> 	mov	DX, [HF_PORT]
  5160 00005186 80C207              <1> 	add	dl, 7			; Status port (HF_PORT+7)
  5161                              <1> 	;MOV	BL,DELAY_1
  5162                              <1> 					; wait for 10 seconds
  5163                              <1> 	;mov 	cx, WAIT_HDU_INT_LO	; 1615h
  5164                              <1> 	;;mov 	bl, WAIT_HDU_INT_HI	;   05h
  5165                              <1> 	;mov	bl, WAIT_HDU_INT_HI + 1
  5166 00005189 B915160500          <1> 	mov	ecx, WAIT_HDU_INT_LH  ; 21/02/2015
  5167                              <1> 	;
  5168                              <1> ;;      mov     byte [wait_count], 0    ; Reset wait counter
  5169                              <1> NB1:	
  5170 0000518E EC                  <1> 	IN	AL,DX			; CHECK STATUS
  5171                              <1> 	;TEST	AL,ST_BUSY
  5172 0000518F 2480                <1> 	and	al, ST_BUSY
  5173                              <1> 	;LOOPNZ	NB1
  5174 00005191 7410                <1> 	JZ	short NB2		; NOT BUSY--LETS GO
  5175                              <1> 	;DEC	BL			
  5176                              <1> 	;JNZ	short NB1		; KEEP TRYING FOR A WHILE
  5177                              <1> 
  5178 00005193 E461                <1> NB1_hi: IN	AL,SYS1			; wait for hi to lo
  5179 00005195 A810                <1> 	TEST	AL,010H			; transition on memory
  5180 00005197 75FA                <1> 	JNZ	SHORT NB1_hi		; refresh.
  5181 00005199 E461                <1> NB1_lo: IN	AL,SYS1
  5182 0000519B A810                <1> 	TEST	AL,010H
  5183 0000519D 74FA                <1> 	JZ	short NB1_lo
  5184 0000519F E2ED                <1> 	LOOP	NB1
  5185                              <1> 	;dec	bl
  5186                              <1> 	;jnz	short NB1
  5187                              <1> 	;
  5188                              <1> ;;      cmp     byte [wait_count], 182  ; 10 seconds (182 timer ticks)
  5189                              <1> ;;	jb	short NB1
  5190                              <1> 	;
  5191                              <1> 	;MOV	[DISK_STATUS1],TIME_OUT	; REPORT TIME OUT ERROR
  5192                              <1> 	;JMP	SHORT NB3
  5193 000051A1 B080                <1> 	mov	al, TIME_OUT
  5194                              <1> NB2:	
  5195                              <1> 	;MOV	byte [DISK_STATUS1],0
  5196                              <1> ;NB3:	
  5197                              <1> 	;POP	eBX
  5198 000051A3 A2[1B5F0100]        <1> 	mov	[DISK_STATUS1], al	;;; will be set after return
  5199                              <1> 	;CMP	byte [DISK_STATUS1],0 	; SET CONDITION CODE FOR CALLER
  5200 000051A8 08C0                <1> 	or	al, al			; (zf = 0 --> timeout)
  5201 000051AA C3                  <1> 	RETn
  5202                              <1> 
  5203                              <1> ;----------------------------------------
  5204                              <1> ;	WAIT FOR DATA REQUEST		:
  5205                              <1> ;----------------------------------------
  5206                              <1> WAIT_DRQ:
  5207                              <1> 	;MOV	CX,DELAY_3
  5208                              <1> 	;MOV	DX,HF_PORT+7
  5209 000051AB 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  5210 000051B2 80C207              <1> 	add	dl, 7
  5211                              <1> 	;;MOV	bl, WAIT_HDU_DRQ_HI	; 0
  5212                              <1> 	;MOV	cx, WAIT_HDU_DRQ_LO	; 1000 (30 milli seconds)
  5213                              <1> 					; (but it is written as 2000
  5214                              <1> 					; micro seconds in ATORGS.ASM file
  5215                              <1> 					; of Award Bios - 1999, D1A0622)
  5216 000051B5 B9E8030000          <1> 	mov 	ecx, WAIT_HDU_DRQ_LH ; 21/02/2015 
  5217 000051BA EC                  <1> WQ_1:	IN	AL,DX			; GET STATUS
  5218 000051BB A808                <1> 	TEST	AL,ST_DRQ		; WAIT FOR DRQ
  5219 000051BD 7516                <1> 	JNZ	short WQ_OK
  5220                              <1> 	;LOOP	WQ_1			; KEEP TRYING FOR A SHORT WHILE
  5221                              <1> WQ_hi:	
  5222 000051BF E461                <1> 	IN	AL,SYS1			; wait for hi to lo
  5223 000051C1 A810                <1> 	TEST	AL,010H			; transition on memory
  5224 000051C3 75FA                <1> 	JNZ	SHORT WQ_hi		; refresh.
  5225 000051C5 E461                <1> WQ_lo:  IN      AL,SYS1
  5226 000051C7 A810                <1> 	TEST	AL,010H
  5227 000051C9 74FA                <1> 	JZ	SHORT WQ_lo
  5228 000051CB E2ED                <1> 	LOOP	WQ_1
  5229                              <1> 
  5230 000051CD C605[1B5F0100]80    <1>         MOV     byte [DISK_STATUS1],TIME_OUT ; ERROR
  5231 000051D4 F9                  <1> 	STC
  5232                              <1> WQ_OK:
  5233 000051D5 C3                  <1> 	RETn
  5234                              <1> ;WQ_OK:	;CLC
  5235                              <1> ;	RETn
  5236                              <1> 
  5237                              <1> ;----------------------------------------
  5238                              <1> ;	CHECK FIXED DISK STATUS 	:
  5239                              <1> ;----------------------------------------
  5240                              <1> CHECK_STATUS:
  5241 000051D6 E813000000          <1> 	CALL	CHECK_ST		; CHECK THE STATUS BYTE
  5242 000051DB 7509                <1> 	JNZ	short CHECK_S1		; AN ERROR WAS FOUND
  5243 000051DD A801                <1> 	TEST	AL,ST_ERROR		; WERE THERE ANY OTHER ERRORS
  5244 000051DF 7405                <1> 	JZ	short CHECK_S1		; NO ERROR REPORTED
  5245 000051E1 E849000000          <1> 	CALL	CHECK_ER		; ERROR REPORTED
  5246                              <1> CHECK_S1:
  5247 000051E6 803D[1B5F0100]00    <1> 	CMP	byte [DISK_STATUS1],0 	; SET STATUS FOR CALLER
  5248 000051ED C3                  <1> 	RETn
  5249                              <1> 
  5250                              <1> ;----------------------------------------
  5251                              <1> ;	CHECK FIXED DISK STATUS BYTE	:
  5252                              <1> ;----------------------------------------
  5253                              <1> CHECK_ST:
  5254                              <1> 	;MOV	DX,HF_PORT+7		; GET THE STATUS
  5255 000051EE 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]
  5256 000051F5 80C207              <1> 	add	dl, 7
  5257                              <1> 	
  5258                              <1> 	; 17/02/2016
  5259                              <1> 	;(http://wiki.osdev.org/ATA_PIO_Mode)
  5260                              <1> 	;"delay 400ns to allow drive to set new values of BSY and DRQ"
  5261 000051F8 EC                  <1> 	IN	AL,DX
  5262                              <1> 	;in	al, dx ; 100ns
  5263                              <1> 	;in	al, dx ; 100ns
  5264                              <1>  	;in	al, dx ; 100ns
  5265                              <1> 	NEWIODELAY ; 18/02/2016 (AWARD BIOS - 1999, 'CKST' in AHSDK.ASM)
  5265 000051F9 E6EB                <2>  out 0ebh,al
  5266                              <1> 	;
  5267 000051FB A2[115F0100]        <1> 	MOV	[HF_STATUS],AL
  5268 00005200 B400                <1> 	MOV	AH,0
  5269 00005202 A880                <1> 	TEST	AL,ST_BUSY		; IF STILL BUSY
  5270 00005204 751A                <1> 	JNZ	short CKST_EXIT		;  REPORT OK
  5271 00005206 B4CC                <1> 	MOV	AH,WRITE_FAULT
  5272 00005208 A820                <1> 	TEST	AL,ST_WRT_FLT		; CHECK FOR WRITE FAULT
  5273 0000520A 7514                <1> 	JNZ	short CKST_EXIT
  5274 0000520C B4AA                <1> 	MOV	AH,NOT_RDY
  5275 0000520E A840                <1> 	TEST	AL,ST_READY		; CHECK FOR NOT READY
  5276 00005210 740E                <1> 	JZ	short CKST_EXIT
  5277 00005212 B440                <1> 	MOV	AH,BAD_SEEK
  5278 00005214 A810                <1> 	TEST	AL,ST_SEEK_COMPL	; CHECK FOR SEEK NOT COMPLETE
  5279 00005216 7408                <1> 	JZ	short CKST_EXIT
  5280 00005218 B411                <1> 	MOV	AH,DATA_CORRECTED
  5281 0000521A A804                <1> 	TEST	AL,ST_CORRCTD		; CHECK FOR CORRECTED ECC
  5282 0000521C 7502                <1> 	JNZ	short CKST_EXIT
  5283 0000521E B400                <1> 	MOV	AH,0
  5284                              <1> CKST_EXIT:
  5285 00005220 8825[1B5F0100]      <1> 	MOV	[DISK_STATUS1],AH	; SET ERROR FLAG
  5286 00005226 80FC11              <1> 	CMP	AH,DATA_CORRECTED	; KEEP GOING WITH DATA CORRECTED
  5287 00005229 7403                <1> 	JZ	short CKST_EX1
  5288 0000522B 80FC00              <1> 	CMP	AH,0
  5289                              <1> CKST_EX1:
  5290 0000522E C3                  <1> 	RETn
  5291                              <1> 
  5292                              <1> ;----------------------------------------
  5293                              <1> ;	CHECK FIXED DISK ERROR REGISTER :
  5294                              <1> ;----------------------------------------
  5295                              <1> CHECK_ER:
  5296                              <1> 	;MOV	DX, HF_PORT+1		; GET THE ERROR REGISTER
  5297 0000522F 668B15[A0640000]    <1> 	mov	dx, [HF_PORT]		;
  5298 00005236 FEC2                <1> 	inc	dl
  5299 00005238 EC                  <1> 	IN	AL,DX
  5300 00005239 A2[125F0100]        <1> 	MOV	[HF_ERROR],AL
  5301 0000523E 53                  <1> 	PUSH	eBX ; 21/02/2015
  5302 0000523F B908000000          <1> 	MOV	eCX,8			; TEST ALL 8 BITS
  5303 00005244 D0E0                <1> CK1:	SHL	AL,1			; MOVE NEXT ERROR BIT TO CARRY
  5304 00005246 7202                <1> 	JC	short CK2		; FOUND THE ERROR
  5305 00005248 E2FA                <1> 	LOOP	CK1			; KEEP TRYING
  5306 0000524A BB[94640000]        <1> CK2:	MOV	eBX, ERR_TBL		; COMPUTE ADDRESS OF
  5307 0000524F 01CB                <1> 	ADD	eBX,eCX			; ERROR CODE
  5308                              <1> 	;;MOV	AH,BYTE [CS:BX]		; GET ERROR CODE
  5309                              <1> 	;mov	ah, [bx]
  5310 00005251 8A23                <1> 	mov	ah, [ebx] ; 21/02/2015	
  5311 00005253 8825[1B5F0100]      <1> CKEX:	MOV	[DISK_STATUS1],AH	; SAVE ERROR CODE
  5312 00005259 5B                  <1> 	POP	eBX
  5313 0000525A 80FC00              <1> 	CMP	AH,0
  5314 0000525D C3                  <1> 	RETn
  5315                              <1> 
  5316                              <1> ;--------------------------------------------------------
  5317                              <1> ; CHECK_DMA						:
  5318                              <1> ;  -CHECK ES:BX AND # SECTORS TO MAKE SURE THAT IT WILL :
  5319                              <1> ;   FIT WITHOUT SEGMENT OVERFLOW.			:
  5320                              <1> ;  -ES:BX HAS BEEN REVISED TO THE FORMAT SSSS:000X	:
  5321                              <1> ;  -OK IF # SECTORS < 80H (7FH IF LONG READ OR WRITE)	:
  5322                              <1> ;  -OK IF # SECTORS = 80H (7FH) AND BX <= 00H (04H)	:
  5323                              <1> ;  -ERROR OTHERWISE					:
  5324                              <1> ;--------------------------------------------------------
  5325                              <1> CHECK_DMA:
  5326 0000525E 6650                <1> 	PUSH	AX			; SAVE REGISTERS
  5327 00005260 66B80080            <1> 	MOV	AX,8000H		; AH = MAX # SECTORS AL = MAX OFFSET
  5328 00005264 F645FE02            <1>         TEST    byte [CMD_BLOCK+6],ECC_MODE
  5329 00005268 7404                <1> 	JZ	short CKD1
  5330 0000526A 66B8047F            <1> 	MOV	AX,7F04H		; ECC IS 4 MORE BYTES
  5331 0000526E 3A65F9              <1> CKD1:	CMP	AH, [CMD_BLOCK+1] 	; NUMBER OF SECTORS
  5332 00005271 7706                <1> 	JA	short CKDOK		; IT WILL FIT
  5333 00005273 7208                <1> 	JB	short CKDERR		; TOO MANY
  5334 00005275 38D8                <1> 	CMP	AL,BL			; CHECK OFFSET ON MAX SECTORS
  5335 00005277 7204                <1> 	JB	short CKDERR		; ERROR
  5336 00005279 F8                  <1> CKDOK:	CLC				; CLEAR CARRY
  5337 0000527A 6658                <1> 	POP	AX
  5338 0000527C C3                  <1> 	RETn				; NORMAL RETURN
  5339 0000527D F9                  <1> CKDERR: STC				; INDICATE ERROR
  5340 0000527E C605[1B5F0100]09    <1>         MOV     byte [DISK_STATUS1],DMA_BOUNDARY
  5341 00005285 6658                <1> 	POP	AX
  5342 00005287 C3                  <1> 	RETn
  5343                              <1> 
  5344                              <1> ;----------------------------------------
  5345                              <1> ;	SET UP ES:BX-> DISK PARMS	:
  5346                              <1> ;----------------------------------------
  5347                              <1> 					
  5348                              <1> ; INPUT -> DL = 0 based drive number
  5349                              <1> ; OUTPUT -> ES:BX = disk parameter table address
  5350                              <1> 
  5351                              <1> GET_VEC:
  5352                              <1> 	;SUB	AX,AX			; GET DISK PARAMETER ADDRESS
  5353                              <1> 	;MOV	ES,AX
  5354                              <1> 	;TEST	DL,1
  5355                              <1> 	;JZ	short GV_0
  5356                              <1> ;	LES	BX,[HF1_TBL_VEC] 	; ES:BX -> DRIVE PARAMETERS
  5357                              <1> ;	JMP	SHORT GV_EXIT
  5358                              <1> ;GV_0:
  5359                              <1> ;	LES	BX,[HF_TBL_VEC]		; ES:BX -> DRIVE PARAMETERS
  5360                              <1> ;
  5361                              <1> 	;xor	bh, bh
  5362 00005288 31DB                <1> 	xor	ebx, ebx
  5363 0000528A 88D3                <1> 	mov	bl, dl
  5364                              <1> 	;;02/01/2015
  5365                              <1> 	;;shl	bl, 1			; port address offset
  5366                              <1> 	;;mov	ax, [bx+hd_ports]	; Base port address (1F0h, 170h)
  5367                              <1> 	;;shl	bl, 1			; dpt pointer offset
  5368 0000528C C0E302              <1> 	shl	bl, 2	;;
  5369                              <1> 	;add	bx, HF_TBL_VEC		; Disk parameter table pointer
  5370 0000528F 81C3[205F0100]      <1> 	add	ebx, HF_TBL_VEC ; 21/02/2015
  5371                              <1> 	;push	word [bx+2]		; dpt segment
  5372                              <1> 	;pop	es
  5373                              <1> 	;mov	bx, [bx]		; dpt offset
  5374 00005295 8B1B                <1> 	mov	ebx, [ebx]		
  5375                              <1> ;GV_EXIT:
  5376 00005297 C3                  <1> 	RETn
  5377                              <1> 
  5378                              <1> hdc1_int: ; 21/02/2015
  5379                              <1> ;--- HARDWARE INT 76H -- ( IRQ LEVEL  14 ) ----------------------
  5380                              <1> ;								:
  5381                              <1> ;	FIXED DISK INTERRUPT ROUTINE				:
  5382                              <1> ;								:
  5383                              <1> ;----------------------------------------------------------------
  5384                              <1> 
  5385                              <1> ; 22/12/2014
  5386                              <1> ; IBM PC-XT Model 286 System BIOS Source Code - DISK.ASM (HD_INT)
  5387                              <1> ;	 '11/15/85'
  5388                              <1> ; AWARD BIOS 1999 (D1A0622) 
  5389                              <1> ;	Source Code - ATORGS.ASM (INT_HDISK, INT_HDISK1)
  5390                              <1> 
  5391                              <1> ;int_76h:
  5392                              <1> HD_INT:
  5393 00005298 6650                <1> 	PUSH	AX
  5394 0000529A 1E                  <1> 	PUSH	DS
  5395                              <1> 	;CALL	DDS
  5396                              <1> 	; 21/02/2015 (32 bit, 386 pm modification)
  5397 0000529B 66B81000            <1> 	mov	ax, KDATA
  5398 0000529F 8ED8                <1> 	mov 	ds, ax
  5399                              <1> 	;
  5400                              <1> 	;;MOV	@HF_INT_FLAG,0FFH	; ALL DONE
  5401                              <1>         ;mov     byte [CS:HF_INT_FLAG], 0FFh
  5402 000052A1 C605[135F0100]FF    <1> 	mov	byte [HF_INT_FLAG], 0FFh
  5403                              <1> 	;
  5404 000052A8 6652                <1> 	push	dx
  5405 000052AA 66BAF701            <1> 	mov	dx, HDC1_BASEPORT+7	; Status Register (1F7h)
  5406                              <1> 					; Clear Controller
  5407                              <1> Clear_IRQ1415:				; (Award BIOS - 1999)
  5408 000052AE EC                  <1> 	in	al, dx			;
  5409 000052AF 665A                <1> 	pop	dx
  5410                              <1> 	NEWIODELAY
  5410 000052B1 E6EB                <2>  out 0ebh,al
  5411                              <1> 	;
  5412 000052B3 B020                <1> 	MOV	AL,EOI			; NON-SPECIFIC END OF INTERRUPT
  5413 000052B5 E6A0                <1> 	OUT	INTB00,AL		; FOR CONTROLLER #2
  5414                              <1> 	;JMP	$+2			; WAIT
  5415                              <1> 	NEWIODELAY
  5415 000052B7 E6EB                <2>  out 0ebh,al
  5416 000052B9 E620                <1> 	OUT	INTA00,AL		; FOR CONTROLLER #1
  5417 000052BB 1F                  <1> 	POP	DS
  5418                              <1> 	;STI				; RE-ENABLE INTERRUPTS
  5419                              <1> 	;MOV	AX,9100H		; DEVICE POST
  5420                              <1> 	;INT	15H			;  INTERRUPT
  5421                              <1> irq15_iret: ; 25/02/2015
  5422 000052BC 6658                <1> 	POP	AX
  5423 000052BE CF                  <1> 	IRETd				; RETURN FROM INTERRUPT
  5424                              <1> 
  5425                              <1> hdc2_int: ; 21/02/2015
  5426                              <1> ;++++ HARDWARE INT 77H ++ ( IRQ LEVEL  15 ) +++++++++++++++++++++
  5427                              <1> ;								:
  5428                              <1> ;	FIXED DISK INTERRUPT ROUTINE				:
  5429                              <1> ;								:
  5430                              <1> ;++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
  5431                              <1> 
  5432                              <1> ;int_77h:
  5433                              <1> HD1_INT:
  5434 000052BF 6650                <1> 	PUSH	AX
  5435                              <1> 	; Check if that is a spurious IRQ (from slave PIC)
  5436                              <1> 	; 25/02/2015 (source: http://wiki.osdev.org/8259_PIC)
  5437 000052C1 B00B                <1> 	mov	al, 0Bh  ; In-Service Register
  5438 000052C3 E6A0                <1> 	out	0A0h, al
  5439 000052C5 EB00                <1>         jmp short $+2
  5440 000052C7 EB00                <1> 	jmp short $+2
  5441 000052C9 E4A0                <1> 	in	al, 0A0h
  5442 000052CB 2480                <1> 	and 	al, 80h ; bit 7 (is it real IRQ 15 or fake?)
  5443 000052CD 74ED                <1> 	jz	short irq15_iret ; Fake (spurious)IRQ, do not send EOI)
  5444                              <1> 	;
  5445 000052CF 1E                  <1> 	PUSH	DS
  5446                              <1> 	;CALL	DDS
  5447                              <1> 	; 21/02/2015 (32 bit, 386 pm modification)
  5448 000052D0 66B81000            <1> 	mov	ax, KDATA
  5449 000052D4 8ED8                <1> 	mov 	ds, ax
  5450                              <1> 	;
  5451                              <1> 	;;MOV	@HF_INT_FLAG,0FFH	; ALL DONE
  5452                              <1>         ;or      byte [CS:HF_INT_FLAG],0C0h 
  5453 000052D6 800D[135F0100]C0    <1> 	or	byte [HF_INT_FLAG], 0C0h
  5454                              <1> 	;
  5455 000052DD 6652                <1> 	push	dx
  5456 000052DF 66BA7701            <1> 	mov	dx, HDC2_BASEPORT+7	; Status Register (177h)
  5457                              <1> 					; Clear Controller (Award BIOS 1999)
  5458 000052E3 EBC9                <1> 	jmp	short Clear_IRQ1415
  5459                              <1> 
  5460                              <1> 
  5461                              <1> ;%include 'diskdata.inc' ; 11/03/2015
  5462                              <1> ;%include 'diskbss.inc' ; 11/03/2015
  5463                              <1> 
  5464                              <1> 
  5465                              <1> ;////////////////////////////////////////////////////////////////////
  5466                              <1> ;; END OF DISK I/O SYTEM ///
  2675                                  %include 'memory.s'  ; 09/03/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - memory.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 22/07/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; memory.inc (18/10/2015)
    15                              <1> ; ****************************************************************************
    16                              <1> 
    17                              <1> ; MEMORY.ASM - Retro UNIX 386 v1 MEMORY MANAGEMENT FUNCTIONS (PROCEDURES)
    18                              <1> ; Retro UNIX 386 v1 Kernel (unix386.s, v0.2.0.14) - MEMORY.INC
    19                              <1> ; Last Modification: 18/10/2015
    20                              <1> 
    21                              <1> ; ///////// MEMORY MANAGEMENT FUNCTIONS (PROCEDURES) ///////////////
    22                              <1> 
    23                              <1> ;;04/11/2014 (unix386.s)	
    24                              <1> ;PDE_A_PRESENT	equ	1		; Present flag for PDE
    25                              <1> ;PDE_A_WRITE	equ 	2		; Writable (write permission) flag
    26                              <1> ;PDE_A_USER	equ	4		; User (non-system/kernel) page flag
    27                              <1> ;;
    28                              <1> ;PTE_A_PRESENT	equ	1		; Present flag for PTE (bit 0)
    29                              <1> ;PTE_A_WRITE	equ 	2		; Writable (write permission) flag (bit 1)
    30                              <1> ;PTE_A_USER	equ	4		; User (non-system/kernel) page flag (bit 2)
    31                              <1> ;PTE_A_ACCESS   equ	32		; Accessed flag (bit 5) ; 09/03/2015
    32                              <1> 
    33                              <1> ; 27/04/2015
    34                              <1> ; 09/03/2015
    35                              <1> PAGE_SIZE 	equ 4096		; page size in bytes
    36                              <1> PAGE_SHIFT 	equ 12			; page table shift count
    37                              <1> PAGE_D_SHIFT 	equ 22	; 12 + 10	; page directory shift count
    38                              <1> PAGE_OFF	equ 0FFFh		; 12 bit byte offset in page frame
    39                              <1> PTE_MASK 	equ 03FFh		; page table entry mask
    40                              <1> PTE_DUPLICATED  equ 200h		; duplicated page sign (AVL bit 0)
    41                              <1> PDE_A_CLEAR	equ 0F000h		; to clear PDE attribute bits
    42                              <1> PTE_A_CLEAR	equ 0F000h		; to clear PTE attribute bits
    43                              <1> LOGIC_SECT_SIZE equ 512			; logical sector size
    44                              <1> ERR_MAJOR_PF	equ 0E0h		; major error: page fault
    45                              <1> ERR_MINOR_IM	equ 4 ;15/10/2016 (1->4); insufficient (out of) memory
    46                              <1> ERR_MINOR_PV	equ 6 ;15/10/2016 (1->4); protection violation
    47                              <1> SWP_DISK_READ_ERR 	   equ 40
    48                              <1> SWP_DISK_NOT_PRESENT_ERR   equ 41
    49                              <1> SWP_SECTOR_NOT_PRESENT_ERR equ 42
    50                              <1> SWP_NO_FREE_SPACE_ERR      equ 43
    51                              <1> SWP_DISK_WRITE_ERR         equ 44
    52                              <1> SWP_NO_PAGE_TO_SWAP_ERR    equ 45
    53                              <1> PTE_A_ACCESS_BIT equ 5  ; Bit 5 (accessed flag)        
    54                              <1> SECTOR_SHIFT     equ 3  ; sector shift (to convert page block number)
    55                              <1> ; 12/07/2016
    56                              <1> PTE_SHARED	 equ 400h		; AVL bit 1, direct memory access bit	
    57                              <1> 					; (Indicates that the page is not allocated
    58                              <1> 					; for the process, it is a shared or system
    59                              <1>                                         ; page, it must not be deallocated!)
    60                              <1> ;
    61                              <1> ;; Retro Unix 386 v1 - paging method/principles
    62                              <1> ;;
    63                              <1> ;; 10/10/2014
    64                              <1> ;; RETRO UNIX 386 v1 - PAGING METHOD/PRINCIPLES
    65                              <1> ;;
    66                              <1> ;; KERNEL PAGE MAP: 1 to 1 physical memory page map
    67                              <1> ;;	(virtual address = physical address)
    68                              <1> ;; KERNEL PAGE TABLES:
    69                              <1> ;;	Kernel page directory and all page tables are
    70                              <1> ;;	on memory as initialized, as equal to physical memory
    71                              <1> ;;	layout. Kernel pages can/must not be swapped out/in.
    72                              <1> ;;
    73                              <1> ;;	what for: User pages may be swapped out, when accessing
    74                              <1> ;;	a page in kernel/system mode, if it would be swapped out,
    75                              <1> ;;	kernel would have to swap it in! But it is also may be
    76                              <1> ;;	in use by a user process. (In system/kernel mode
    77                              <1> ;;	kernel can access all memory pages even if they are
    78                              <1> ;;	reserved/allocated for user processes. Swap out/in would
    79                              <1> ;;	cause conflicts.) 
    80                              <1> ;;	
    81                              <1> ;;	As result of these conditions,
    82                              <1> ;;	all kernel pages must be initialized as equal to 
    83                              <1> ;;	physical layout for preventing page faults. 
    84                              <1> ;;	Also, calling "allocate page" procedure after
    85                              <1> ;;	a page fault can cause another page fault (double fault)
    86                              <1> ;;	if all kernel page tables would not be initialized.
    87                              <1> ;;
    88                              <1> ;;	[first_page] = Beginning of users space, as offset to 
    89                              <1> ;;	memory allocation table. (double word aligned)
    90                              <1> ;;
    91                              <1> ;;	[next_page] = first/next free space to be searched
    92                              <1> ;;	as offset to memory allocation table. (dw aligned)
    93                              <1> ;;
    94                              <1> ;;	[last_page] = End of memory (users space), as offset
    95                              <1> ;;	to memory allocation table. (double word aligned)
    96                              <1> ;;
    97                              <1> ;; USER PAGE TABLES:
    98                              <1> ;;	Demand paging (& 'copy on write' allocation method) ...
    99                              <1> ;;		'ready only' marked copies of the 
   100                              <1> ;;		parent process's page table entries (for
   101                              <1> ;;		same physical memory).
   102                              <1> ;;		(A page will be copied to a new page after
   103                              <1> ;;		 if it causes R/W page fault.)
   104                              <1> ;;
   105                              <1> ;;	Every user process has own (different)
   106                              <1> ;;	page directory and page tables.	
   107                              <1> ;;
   108                              <1> ;;	Code starts at virtual address 0, always.
   109                              <1> ;;	(Initial value of EIP is 0 in user mode.)
   110                              <1> ;;	(Programs can be written/developed as simple
   111                              <1> ;;	 flat memory programs.)
   112                              <1> ;;
   113                              <1> ;; MEMORY ALLOCATION STRATEGY:
   114                              <1> ;;	Memory page will be allocated by kernel only 
   115                              <1> ;;		(in kernel/system mode only).
   116                              <1> ;;	* After a
   117                              <1> ;;	  - 'not present' page fault
   118                              <1> ;;	  - 'writing attempt on read only page' page fault 	 	
   119                              <1> ;;	* For loading (opening, reading) a file or disk/drive
   120                              <1> ;;	* As responce to 'allocate additional memory blocks' 
   121                              <1> ;;	  request by running process.
   122                              <1> ;;	* While creating a process, allocating a new buffer,
   123                              <1> ;;	  new page tables etc.
   124                              <1> ;;
   125                              <1> ;;	At first,
   126                              <1> ;;	- 'allocate page' procedure will be called;
   127                              <1> ;,	   if it will return with a valid (>0) physical address
   128                              <1> ;;	   (that means the relevant M.A.T. bit has been RESET)	
   129                              <1> ;;	   relevant memory page/block will be cleared (zeroed).
   130                              <1> ;;	- 'allocate page' will be called for allocating page
   131                              <1> ;;	   directory, page table and running space (data/code).
   132                              <1> ;;	- every successful 'allocate page' call will decrease
   133                              <1> ;;	  'free_pages' count (pointer).
   134                              <1> ;;	- 'out of (insufficient) memory error' will be returned
   135                              <1> ;;	  if 'free_pages' points to a ZERO.
   136                              <1> ;;	- swapping out and swapping in (if it is not a new page)
   137                              <1> ;;	  procedures will be called as responce to 'out of memory'
   138                              <1> ;;	  error except errors caused by attribute conflicts.
   139                              <1> ;;	 (swapper functions)	 
   140                              <1> ;;					
   141                              <1> ;;	At second,
   142                              <1> ;;	- page directory entry will be updated then page table
   143                              <1> ;;	  entry will be updated.		
   144                              <1> ;;
   145                              <1> ;; MEMORY ALLOCATION TABLE FORMAT:
   146                              <1> ;;	- M.A.T. has a size according to available memory as
   147                              <1> ;;	  follows:
   148                              <1> ;;		  - 1 (allocation) bit per 1 page (4096 bytes)
   149                              <1> ;;		  - a bit with value of 0 means allocated page
   150                              <1> ;;		  - a bit with value of 1 means a free page
   151                              <1> ;,	- 'free_pages' pointer holds count of free pages
   152                              <1> ;;	  depending on M.A.T.
   153                              <1> ;;		(NOTE: Free page count will not be checked
   154                              <1> ;;		again -on M.A.T.- after initialization. 
   155                              <1> ;;		Kernel will trust on initial count.)
   156                              <1> ;,	- 'free_pages' count will be decreased by allocation
   157                              <1> ;;	  and it will be increased by deallocation procedures.
   158                              <1> ;;	
   159                              <1> ;;	- Available memory will be calculated during
   160                              <1> ;;	  the kernel's initialization stage (in real mode).
   161                              <1> ;;	  Memory allocation table and kernel page tables 
   162                              <1> ;;	  will be formatted/sized as result of available
   163                              <1> ;;	  memory calculation before paging is enabled.
   164                              <1> ;;
   165                              <1> ;; For 4GB Available/Present Memory: (max. possible memory size)
   166                              <1> ;;	- Memory Allocation Table size will be 128 KB.
   167                              <1> ;;	- Memory allocation for kernel page directory size 
   168                              <1> ;;	  is always 4 KB. (in addition to total allocation size
   169                              <1> ;;	  for page tables)
   170                              <1> ;;	- Memory allocation for kernel page tables (1024 tables)
   171                              <1> ;;	  is 4 MB (1024*4*1024 bytes).
   172                              <1> ;;	- User (available) space will be started 
   173                              <1> ;;	  at 6th MB of the memory (after 1MB+4MB).
   174                              <1> ;;	- The first 640 KB is for kernel's itself plus
   175                              <1> ;;	  memory allocation table and kernel's page directory
   176                              <1> ;;	  (D0000h-EFFFFh may be used as kernel space...)	
   177                              <1> ;;	- B0000h to B7FFFh address space (32 KB) will be used
   178                              <1> ;; 	  for buffers.
   179                              <1> ;;	- ROMBIOS, VIDEO BUFFER and VIDEO ROM space are reserved.
   180                              <1> ;,	  (A0000h-AFFFFh, C0000h-CFFFFh, F0000h-FFFFFh)
   181                              <1> ;;	- Kernel page tables start at 100000h (2nd MB)
   182                              <1> ;;
   183                              <1> ;; For 1GB Available Memory:
   184                              <1> ;;	- Memory Allocation Table size will be 32 KB.
   185                              <1> ;;	- Memory allocation for kernel page directory size 
   186                              <1> ;;	  is always 4 KB. (in addition to total allocation size
   187                              <1> ;;	  for page tables)
   188                              <1> ;;	- Memory allocation for kernel page tables (256 tables)
   189                              <1> ;;	  is 1 MB (256*4*1024 bytes).
   190                              <1> ;;	- User (available) space will be started 
   191                              <1> ;;	  at 3th MB of the memory (after 1MB+1MB).
   192                              <1> ;;	- The first 640 KB is for kernel's itself plus
   193                              <1> ;;	  memory allocation table and kernel's page directory
   194                              <1> ;;	  (D0000h-EFFFFh may be used as kernel space...)	
   195                              <1> ;;	- B0000h to B7FFFh address space (32 KB) will be used
   196                              <1> ;; 	  for buffers.
   197                              <1> ;;	- ROMBIOS, VIDEO BUFFER and VIDEO ROM space are reserved.
   198                              <1> ;,	  (A0000h-AFFFFh, C0000h-CFFFFh, F0000h-FFFFFh)
   199                              <1> ;;	- Kernel page tables start at 100000h (2nd MB).	
   200                              <1> ;;
   201                              <1> ;;
   202                              <1> 
   203                              <1> 
   204                              <1> ;;************************************************************************************
   205                              <1> ;; 
   206                              <1> ;; RETRO UNIX 386 v1 - Paging (Method for Copy On Write paging principle)
   207                              <1> ;; DEMAND PAGING - PARENT&CHILD PAGE TABLE DUPLICATION PRINCIPLES (23/04/2015)
   208                              <1> 
   209                              <1> ;; Main factor: "sys fork" system call 
   210                              <1> ;;	
   211                              <1> ;; 		FORK
   212                              <1> ;;                      |----> parent - duplicated PTEs, read only pages
   213                              <1> ;;  writable pages ---->|
   214                              <1> ;;                      |----> child - duplicated PTEs, read only pages
   215                              <1> ;; 
   216                              <1> ;; AVL bit (0) of Page Table Entry is used as duplication sign 
   217                              <1> ;; 
   218                              <1> ;; AVL Bit 0 [PTE Bit 9] = 'Duplicated PTE belongs to child' sign/flag (if it is set)
   219                              <1> ;; Note: Dirty bit (PTE bit 6) may be used instead of AVL bit 0 (PTE bit 9)
   220                              <1> ;;       -while R/W bit is 0-. 
   221                              <1> ;; 
   222                              <1> ;; Duplicate page tables with writable pages (the 1st sys fork in the process):
   223                              <1> ;; # Parent's Page Table Entries are updated to point same pages as read only, 
   224                              <1> ;;   as duplicated PTE bit  -AVL bit 0, PTE bit 9- are reset/clear.
   225                              <1> ;; # Then Parent's Page Table is copied to Child's Page Table.
   226                              <1> ;; # Child's Page Table Entries are updated as duplicated child bit
   227                              <1> ;;   -AVL bit 0, PTE bit 9- is set.	  
   228                              <1> ;; 
   229                              <1> ;; Duplicate page tables with read only pages (several sys fork system calls):
   230                              <1> ;; # Parent's read only pages are copied to new child pages. 
   231                              <1> ;;   Parent's PTE attributes are not changed.
   232                              <1> ;;   (Because, there is another parent-child fork before this fork! We must not
   233                              <1> ;;    destroy/mix previous fork result).
   234                              <1> ;; # Child's Page Table Entries (which are corresponding to Parent's 
   235                              <1> ;;   read only pages) are set as writable (while duplicated PTE bit is clear). 
   236                              <1> ;; # Parent's PTEs with writable page attribute are updated to point same pages 
   237                              <1> ;;   as read only, (while) duplicated PTE bit is reset (clear).
   238                              <1> ;; # Parent's Page Table Entries (with writable page attribute) are duplicated 
   239                              <1> ;;   as Child's Page Table Entries without copying actual page.
   240                              <1> ;; # Child 's Page Table Entries (which are corresponding to Parent's writable 
   241                              <1> ;;   pages) are updated as duplicated PTE bit (AVL bit 0, PTE bit 9- is set.
   242                              <1> ;; 
   243                              <1> ;; !? WHAT FOR (duplication after duplication):
   244                              <1> ;; In UNIX method for sys fork (a typical 'fork' application in /etc/init)
   245                              <1> ;; program/executable code continues from specified location as child process, 
   246                              <1> ;; returns back previous code location as parent process, every child after 
   247                              <1> ;; every sys fork uses last image of code and data just prior the fork.
   248                              <1> ;; Even if the parent code changes data, the child will not see the changed data 
   249                              <1> ;; after the fork. In Retro UNIX 8086 v1, parent's process segment (32KB)
   250                              <1> ;; was copied to child's process segment (all of code and data) according to
   251                              <1> ;; original UNIX v1 which copies all of parent process code and data -core- 
   252                              <1> ;; to child space -core- but swaps that core image -of child- on to disk.
   253                              <1> ;; If I (Erdogan Tan) would use a method of to copy parent's core
   254                              <1> ;; (complete running image of parent process) to the child process; 
   255                              <1> ;; for big sizes, i would force Retro UNIX 386 v1 to spend many memory pages 
   256                              <1> ;; and times only for a sys fork. (It would excessive reservation for sys fork,
   257                              <1> ;; because sys fork usually is prior to sys exec; sys exec always establishes
   258                              <1> ;; a new/fresh core -running space-, by clearing all code/data content). 
   259                              <1> ;; 'Read Only' page flag ensures page fault handler is needed only for a few write
   260                              <1> ;; attempts between sys fork and sys exec, not more... (I say so by thinking 
   261                              <1> ;; of "/etc/init" content, specially.) sys exec will clear page tables and
   262                              <1> ;; new/fresh pages will be used to load and run new executable/program.
   263                              <1> ;; That is what for i have preferred "copy on write", "duplication" method
   264                              <1> ;; for sharing same read only pages between parent and child processes.
   265                              <1> ;; That is a pitty i have to use new private flag (AVL bit 0, "duplicated PTE 
   266                              <1> ;; belongs to child" sign) for cooperation on duplicated pages between a parent 
   267                              <1> ;; and it's child processes; otherwise parent process would destroy data belongs
   268                              <1> ;; to its child or vice versa; or some pages would remain unclaimed 
   269                              <1> ;; -deallocation problem-.
   270                              <1> ;; Note: to prevent conflicts, read only pages must not be swapped out... 
   271                              <1> ;; 
   272                              <1> ;; WHEN PARENT TRIES TO WRITE IT'S READ ONLY (DUPLICATED) PAGE:
   273                              <1> ;; # Page fault handler will do those:
   274                              <1> ;;   - 'Duplicated PTE' flag (PTE bit 9) is checked (on the failed PTE).
   275                              <1> ;;   - If it is reset/clear, there is a child uses same page.
   276                              <1> ;;   - Parent's read only page -previous page- is copied to a new writable page. 
   277                              <1> ;;   - Parent's PTE is updated as writable page, as unique page (AVL=0)
   278                              <1> ;;   - (Page fault handler whill check this PTE later, if child process causes to
   279                              <1> ;;     page fault due to write attempt on read only page. Of course, the previous 
   280                              <1> ;;     read only page will be converted to writable and unique page which belongs
   281                              <1> ;;     to child process.)	
   282                              <1> ;; WHEN CHILD TRIES TO WRITE IT'S READ ONLY (DUPLICATED) PAGE:
   283                              <1> ;; # Page fault handler will do those:
   284                              <1> ;;   - 'Duplicated PTE' flag (PTE bit 9) is checked (on the failed PTE).
   285                              <1> ;;   - If it is set, there is a parent uses -or was using- same page.
   286                              <1> ;;   - Same PTE address within parent's page table is checked if it has same page
   287                              <1> ;;     address or not. 
   288                              <1> ;;   - If parent's PTE has same address, child will continue with a new writable page.
   289                              <1> ;;     Parent's PTE will point to same (previous) page as writable, unique (AVL=0).	
   290                              <1> ;;   - If parent's PTE has different address, child will continue with it's 
   291                              <1> ;;     own/same page but read only flag (0) will be changed to writable flag (1) and
   292                              <1> ;;     'duplicated PTE (belongs to child)' flag/sign will be cleared/reset. 	  	
   293                              <1> ;; 
   294                              <1> ;; NOTE: When a child process is terminated, read only flags of parent's page tables
   295                              <1> ;;       will be set as writable (and unique) in case of child process was using 
   296                              <1> ;;       same pages with duplicated child PTE sign... Depending on sys fork and 
   297                              <1> ;;       duplication method details, it is not possible multiple child processes
   298                              <1> ;;       were using same page with duplicated PTEs.
   299                              <1> ;; 
   300                              <1> ;;************************************************************************************   
   301                              <1> 
   302                              <1> ;; 08/10/2014
   303                              <1> ;; 11/09/2014 - Retro UNIX 386 v1 PAGING (further) draft
   304                              <1> ;;		by Erdogan Tan (Based on KolibriOS 'memory.inc')
   305                              <1> 
   306                              <1> ;; 'allocate_page' code is derived and modified from KolibriOS
   307                              <1> ;; 'alloc_page' procedure in 'memory.inc' 
   308                              <1> ;; (25/08/2014, Revision: 5057) file 
   309                              <1> ;; by KolibriOS Team (2004-2012)
   310                              <1> 
   311                              <1> allocate_page:
   312                              <1> 	; 01/07/2015
   313                              <1> 	; 05/05/2015
   314                              <1> 	; 30/04/2015
   315                              <1> 	; 16/10/2014
   316                              <1> 	; 08/10/2014
   317                              <1> 	; 09/09/2014 (Retro UNIX 386 v1 - beginning)
   318                              <1> 	;
   319                              <1> 	; INPUT -> none
   320                              <1> 	;
   321                              <1> 	; OUTPUT ->
   322                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS OF THE ALLOCATED PAGE
   323                              <1> 	;	(corresponding MEMORY ALLOCATION TABLE bit is RESET)
   324                              <1> 	;
   325                              <1> 	;	CF = 1 and EAX = 0 
   326                              <1> 	; 		   if there is not a free page to be allocated	
   327                              <1> 	;
   328                              <1> 	; Modified Registers -> none (except EAX)
   329                              <1> 	;
   330 000052E5 A1[885E0100]        <1> 	mov	eax, [free_pages]
   331 000052EA 21C0                <1> 	and	eax, eax
   332 000052EC 7438                <1> 	jz	short out_of_memory
   333                              <1> 	;
   334 000052EE 53                  <1> 	push	ebx
   335 000052EF 51                  <1> 	push	ecx
   336                              <1> 	;
   337 000052F0 BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL   ; Memory Allocation Table offset
   338 000052F5 89D9                <1> 	mov	ecx, ebx
   339                              <1>  				     ; NOTE: 32 (first_page) is initial
   340                              <1> 				     ; value of [next_page].
   341                              <1> 				     ; It points to the first available
   342                              <1> 				     ; page block for users (ring 3) ...	
   343                              <1> 				     ; (MAT offset 32 = 1024/32)	
   344                              <1> 				     ; (at the of the first 4 MB)		
   345 000052F7 031D[8C5E0100]      <1> 	add	ebx, [next_page] ; Free page searching starts from here
   346                              <1> 				 ; next_free_page >> 5
   347 000052FD 030D[905E0100]      <1> 	add	ecx, [last_page] ; Free page searching ends here
   348                              <1> 				 ; (total_pages - 1) >> 5
   349                              <1> al_p_scan:
   350 00005303 39CB                <1> 	cmp	ebx, ecx
   351 00005305 770A                <1> 	ja	short al_p_notfound
   352                              <1> 	;
   353                              <1> 	; 01/07/2015
   354                              <1> 	; AMD64 Architecture Programmers Manual
   355                              <1> 	; Volume 3:
   356                              <1> 	; General-Purpose and System Instructions
   357                              <1> 	;
   358                              <1> 	; BSF - Bit Scan Forward
   359                              <1> 	;
   360                              <1> 	;   Searches the value in a register or a memory location
   361                              <1> 	;   (second operand) for the least-significant set bit. 
   362                              <1> 	;   If a set bit is found, the instruction clears the zero flag (ZF)
   363                              <1> 	;   and stores the index of the least-significant set bit in a destination
   364                              <1> 	;   register (first operand). If the second operand contains 0, 
   365                              <1> 	;   the instruction sets ZF to 1 and does not change the contents of the 
   366                              <1> 	;   destination register. The bit index is an unsigned offset from bit 0 
   367                              <1> 	;   of the searched value
   368                              <1> 	;
   369 00005307 0FBC03              <1> 	bsf	eax, [ebx] ; Scans source operand for first bit set (1).
   370                              <1> 			   ; Clear ZF if a bit is found set (1) and 
   371                              <1> 			   ; loads the destination with an index to
   372                              <1> 			   ; first set bit. (0 -> 31) 
   373                              <1> 			   ; Sets ZF to 1 if no bits are found set.
   374 0000530A 7525                <1> 	jnz	short al_p_found ; ZF = 0 -> a free page has been found
   375                              <1> 			 ;
   376                              <1> 			 ; NOTE:  a Memory Allocation Table bit 
   377                              <1> 			 ;	  with value of 1 means 
   378                              <1> 			 ;	  the corresponding page is free 
   379                              <1> 			 ;	  (Retro UNIX 386 v1 feature only!)
   380 0000530C 83C304              <1> 	add	ebx, 4
   381                              <1> 			 ; We return back for searching next page block
   382                              <1> 			 ; NOTE: [free_pages] is not ZERO; so, 
   383                              <1> 			 ;	 we always will find at least 1 free page here.
   384 0000530F EBF2                <1>         jmp     short al_p_scan
   385                              <1> 	;
   386                              <1> al_p_notfound:
   387 00005311 81E900001000        <1> 	sub	ecx, MEM_ALLOC_TBL
   388 00005317 890D[8C5E0100]      <1> 	mov	[next_page], ecx ; next/first free page = last page 
   389                              <1> 				 ; (deallocate_page procedure will change it)
   390 0000531D 31C0                <1> 	xor	eax, eax
   391 0000531F A3[885E0100]        <1> 	mov	[free_pages], eax ; 0
   392 00005324 59                  <1> 	pop	ecx
   393 00005325 5B                  <1> 	pop	ebx
   394                              <1> 	;
   395                              <1> out_of_memory:
   396 00005326 E85B040000          <1> 	call	swap_out
   397 0000532B 7325                <1> 	jnc	short al_p_ok  ; [free_pages] = 0, re-allocation by swap_out
   398                              <1> 	;
   399 0000532D 29C0                <1> 	sub 	eax, eax ; 0
   400 0000532F F9                  <1> 	stc
   401 00005330 C3                  <1> 	retn
   402                              <1> 
   403                              <1> al_p_found:
   404 00005331 89D9                <1> 	mov	ecx, ebx
   405 00005333 81E900001000        <1> 	sub	ecx, MEM_ALLOC_TBL
   406 00005339 890D[8C5E0100]      <1> 	mov	[next_page], ecx ; Set first free page searching start
   407                              <1> 				 ; address/offset (to the next)
   408 0000533F FF0D[885E0100]      <1>         dec     dword [free_pages] ; 1 page has been allocated (X = X-1) 
   409                              <1> 	;
   410 00005345 0FB303              <1> 	btr	[ebx], eax	 ; The destination bit indexed by the source value
   411                              <1> 				 ; is copied into the Carry Flag and then cleared
   412                              <1> 				 ; in the destination.
   413                              <1> 				 ;
   414                              <1> 				 ; Reset the bit which is corresponding to the 
   415                              <1> 				 ; (just) allocated page.
   416                              <1> 	; 01/07/2015 (4*8 = 32, 1 allocation byte = 8 pages)	
   417 00005348 C1E103              <1> 	shl	ecx, 3		 ; (page block offset * 32) + page index
   418 0000534B 01C8                <1> 	add	eax, ecx	 ; = page number
   419 0000534D C1E00C              <1> 	shl	eax, 12		 ; physical address of the page (flat/real value)
   420                              <1> 	; EAX = physical address of memory page
   421                              <1> 	;
   422                              <1> 	; NOTE: The relevant page directory and page table entry will be updated
   423                              <1> 	;       according to this EAX value...
   424 00005350 59                  <1> 	pop	ecx
   425 00005351 5B                  <1> 	pop	ebx
   426                              <1> al_p_ok:
   427 00005352 C3                  <1> 	retn
   428                              <1> 
   429                              <1> 
   430                              <1> make_page_dir:
   431                              <1> 	; 18/04/2015
   432                              <1> 	; 12/04/2015
   433                              <1> 	; 23/10/2014
   434                              <1> 	; 16/10/2014
   435                              <1> 	; 09/10/2014 ; (Retro UNIX 386 v1 - beginning)
   436                              <1> 	;
   437                              <1> 	; INPUT ->
   438                              <1> 	;	none
   439                              <1> 	; OUTPUT ->
   440                              <1> 	;	(EAX = 0)
   441                              <1> 	;	cf = 1 -> insufficient (out of) memory error
   442                              <1> 	;	cf = 0 ->
   443                              <1> 	;	u.pgdir = page directory (physical) address of the current
   444                              <1> 	;		  process/user.
   445                              <1> 	;
   446                              <1> 	; Modified Registers -> EAX
   447                              <1> 	;
   448 00005353 E88DFFFFFF          <1> 	call	allocate_page
   449 00005358 7216                <1> 	jc	short mkpd_error
   450                              <1> 	;
   451 0000535A A3[B8030300]        <1> 	mov	[u.pgdir], eax    ; Page dir address for current user/process
   452                              <1> 				  ; (Physical address)
   453                              <1> clear_page:
   454                              <1> 	; 18/04/2015
   455                              <1> 	; 09/10/2014 ; (Retro UNIX 386 v1 - beginning)
   456                              <1> 	;
   457                              <1> 	; INPUT ->
   458                              <1> 	;	EAX = physical address of the page
   459                              <1> 	; OUTPUT ->
   460                              <1> 	;	all bytes of the page will be cleared
   461                              <1> 	;
   462                              <1> 	; Modified Registers -> none
   463                              <1> 	;
   464 0000535F 57                  <1> 	push	edi
   465 00005360 51                  <1> 	push	ecx
   466 00005361 50                  <1> 	push	eax
   467 00005362 B900040000          <1> 	mov	ecx, PAGE_SIZE / 4
   468 00005367 89C7                <1> 	mov	edi, eax
   469 00005369 31C0                <1> 	xor	eax, eax
   470 0000536B F3AB                <1> 	rep	stosd
   471 0000536D 58                  <1> 	pop	eax
   472 0000536E 59                  <1> 	pop	ecx
   473 0000536F 5F                  <1> 	pop	edi
   474                              <1> mkpd_error:
   475                              <1> mkpt_error:
   476 00005370 C3                  <1> 	retn
   477                              <1> 
   478                              <1> make_page_table:
   479                              <1> 	; 23/06/2015
   480                              <1> 	; 18/04/2015
   481                              <1> 	; 12/04/2015
   482                              <1> 	; 16/10/2014
   483                              <1> 	; 09/10/2014 ; (Retro UNIX 386 v1 - beginning)
   484                              <1> 	;
   485                              <1> 	; INPUT ->
   486                              <1> 	;	EBX = virtual (linear) address
   487                              <1> 	;	ECX = page table attributes (lower 12 bits)
   488                              <1> 	;	      (higher 20 bits must be ZERO)
   489                              <1> 	;	      (bit 0 must be 1)	 
   490                              <1> 	;	u.pgdir = page directory (physical) address
   491                              <1> 	; OUTPUT ->
   492                              <1> 	;	EDX = Page directory entry address
   493                              <1> 	;	EAX = Page table address
   494                              <1> 	;	cf = 1 -> insufficient (out of) memory error
   495                              <1> 	;	cf = 0 -> page table address in the PDE (EDX)
   496                              <1> 	;
   497                              <1> 	; Modified Registers -> EAX, EDX
   498                              <1> 	;
   499 00005371 E86FFFFFFF          <1> 	call	allocate_page
   500 00005376 72F8                <1> 	jc	short mkpt_error
   501 00005378 E811000000          <1> 	call	set_pde	
   502 0000537D EBE0                <1> 	jmp	short clear_page
   503                              <1> 
   504                              <1> make_page:
   505                              <1> 	; 24/07/2015
   506                              <1> 	; 23/06/2015 ; (Retro UNIX 386 v1 - beginning)
   507                              <1> 	;
   508                              <1> 	; INPUT ->
   509                              <1> 	;	EBX = virtual (linear) address
   510                              <1> 	;	ECX = page attributes (lower 12 bits)
   511                              <1> 	;	      (higher 20 bits must be ZERO)
   512                              <1> 	;	      (bit 0 must be 1)	 
   513                              <1> 	;	u.pgdir = page directory (physical) address
   514                              <1> 	; OUTPUT ->
   515                              <1> 	;	EBX = Virtual address
   516                              <1> 	;	(EDX = PTE value)
   517                              <1> 	;	EAX = Physical address
   518                              <1> 	;	cf = 1 -> insufficient (out of) memory error
   519                              <1> 	;
   520                              <1> 	; Modified Registers -> EAX, EDX
   521                              <1> 	;
   522 0000537F E861FFFFFF          <1> 	call	allocate_page
   523 00005384 7207                <1> 	jc	short mkp_err
   524 00005386 E821000000          <1> 	call	set_pte	
   525 0000538B 73D2                <1> 	jnc	short clear_page ; 18/04/2015
   526                              <1> mkp_err:
   527 0000538D C3                  <1> 	retn
   528                              <1> 
   529                              <1> 
   530                              <1> set_pde:	; Set page directory entry (PDE)
   531                              <1> 	; 20/07/2015
   532                              <1> 	; 18/04/2015
   533                              <1> 	; 12/04/2015
   534                              <1> 	; 23/10/2014
   535                              <1> 	; 10/10/2014 ; (Retro UNIX 386 v1 - beginning)
   536                              <1> 	;
   537                              <1> 	; INPUT ->
   538                              <1> 	;	EAX = physical address
   539                              <1> 	;	      (use present value if EAX = 0)
   540                              <1> 	;	EBX = virtual (linear) address
   541                              <1> 	;	ECX = page table attributes (lower 12 bits)
   542                              <1> 	;	      (higher 20 bits must be ZERO)
   543                              <1> 	;	      (bit 0 must be 1)	 
   544                              <1> 	;	u.pgdir = page directory (physical) address
   545                              <1> 	; OUTPUT ->
   546                              <1> 	;	EDX = PDE address
   547                              <1> 	;	EAX = page table address (physical)
   548                              <1> 	;	;(CF=1 -> Invalid page address)
   549                              <1> 	;
   550                              <1> 	; Modified Registers -> EDX
   551                              <1> 	;
   552 0000538E 89DA                <1> 	mov	edx, ebx
   553 00005390 C1EA16              <1> 	shr	edx, PAGE_D_SHIFT ; 22
   554 00005393 C1E202              <1> 	shl	edx, 2 ; offset to page directory (1024*4)
   555 00005396 0315[B8030300]      <1> 	add	edx, [u.pgdir]
   556                              <1> 	;
   557 0000539C 21C0                <1> 	and	eax, eax
   558 0000539E 7506                <1> 	jnz	short spde_1
   559                              <1> 	;
   560 000053A0 8B02                <1> 	mov	eax, [edx]  ; old PDE value
   561                              <1> 	;test	al, 1
   562                              <1> 	;jz	short spde_2
   563 000053A2 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h  ; clear lower 12 bits
   564                              <1> spde_1:
   565                              <1> 	;and	cx, 0FFFh
   566 000053A6 8902                <1> 	mov	[edx], eax
   567 000053A8 66090A              <1> 	or	[edx], cx
   568 000053AB C3                  <1> 	retn
   569                              <1> ;spde_2: ; error
   570                              <1> ;	stc
   571                              <1> ;	retn
   572                              <1> 
   573                              <1> set_pte:	; Set page table entry (PTE)
   574                              <1> 	; 24/07/2015
   575                              <1> 	; 20/07/2015
   576                              <1> 	; 23/06/2015
   577                              <1> 	; 18/04/2015
   578                              <1> 	; 12/04/2015
   579                              <1> 	; 10/10/2014 ; (Retro UNIX 386 v1 - beginning)
   580                              <1> 	;
   581                              <1> 	; INPUT ->
   582                              <1> 	;	EAX = physical page address
   583                              <1> 	;	      (use present value if EAX = 0)
   584                              <1> 	;	EBX = virtual (linear) address
   585                              <1> 	;	ECX = page attributes (lower 12 bits)
   586                              <1> 	;	      (higher 20 bits must be ZERO)
   587                              <1> 	;	      (bit 0 must be 1)	 
   588                              <1> 	;	u.pgdir = page directory (physical) address
   589                              <1> 	; OUTPUT ->
   590                              <1> 	;	EAX = physical page address
   591                              <1> 	;	(EDX = PTE value)
   592                              <1> 	;	EBX = virtual address
   593                              <1> 	;
   594                              <1> 	;	CF = 1 -> error
   595                              <1> 	;
   596                              <1> 	; Modified Registers -> EAX, EDX
   597                              <1> 	;
   598 000053AC 50                  <1> 	push	eax
   599 000053AD A1[B8030300]        <1> 	mov	eax, [u.pgdir] ; 20/07/2015
   600 000053B2 E837000000          <1> 	call 	get_pde
   601                              <1> 		; EDX = PDE address
   602                              <1> 		; EAX = PDE value
   603 000053B7 5A                  <1> 	pop	edx ; physical page address
   604 000053B8 722A                <1> 	jc	short spte_err ; PDE not present
   605                              <1> 	;
   606 000053BA 53                  <1> 	push	ebx ; 24/07/2015
   607 000053BB 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear lower 12 bits
   608                              <1> 			    ; EDX = PT address (physical)	
   609 000053BF C1EB0C              <1> 	shr	ebx, PAGE_SHIFT ; 12
   610 000053C2 81E3FF030000        <1> 	and	ebx, PTE_MASK	; 03FFh
   611                              <1> 			 ; clear higher 10 bits (PD bits)
   612 000053C8 C1E302              <1> 	shl	ebx, 2   ; offset to page table (1024*4)
   613 000053CB 01C3                <1> 	add	ebx, eax
   614                              <1> 	;
   615 000053CD 8B03                <1> 	mov	eax, [ebx] ; Old PTE value
   616 000053CF A801                <1> 	test	al, 1
   617 000053D1 740C                <1> 	jz	short spte_0
   618 000053D3 09D2                <1> 	or	edx, edx
   619 000053D5 750F                <1> 	jnz	short spte_1
   620 000053D7 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear lower 12 bits
   621 000053DB 89C2                <1> 	mov	edx, eax
   622 000053DD EB09                <1> 	jmp	short spte_2	
   623                              <1> spte_0:
   624                              <1> 	; If this PTE contains a swap (disk) address,
   625                              <1> 	; it can be updated by using 'swap_in' procedure
   626                              <1> 	; only!
   627 000053DF 21C0                <1> 	and	eax, eax
   628 000053E1 7403                <1> 	jz	short spte_1
   629                              <1> 	; 24/07/2015
   630                              <1> 	; swapped page ! (on disk)
   631 000053E3 5B                  <1> 	pop	ebx
   632                              <1> spte_err:
   633 000053E4 F9                  <1> 	stc
   634 000053E5 C3                  <1> 	retn
   635                              <1> spte_1: 
   636 000053E6 89D0                <1> 	mov	eax, edx
   637                              <1> spte_2:
   638 000053E8 09CA                <1> 	or	edx, ecx
   639                              <1> 	; 23/06/2015
   640 000053EA 8913                <1> 	mov	[ebx], edx ; PTE value in EDX
   641                              <1> 	; 24/07/2015
   642 000053EC 5B                  <1> 	pop	ebx
   643 000053ED C3                  <1> 	retn
   644                              <1> 
   645                              <1> get_pde:	; Get present value of the relevant PDE
   646                              <1> 	; 20/07/2015
   647                              <1> 	; 18/04/2015
   648                              <1> 	; 12/04/2015
   649                              <1> 	; 10/10/2014 ; (Retro UNIX 386 v1 - beginning)
   650                              <1> 	;
   651                              <1> 	; INPUT ->
   652                              <1> 	;	EBX = virtual (linear) address
   653                              <1> 	;	EAX = page directory (physical) address
   654                              <1> 	; OUTPUT ->
   655                              <1> 	;	EDX = Page directory entry address
   656                              <1> 	;	EAX = Page directory entry value
   657                              <1> 	;	CF = 1 -> PDE not present or invalid ? 
   658                              <1> 	; Modified Registers -> EDX, EAX
   659                              <1> 	;
   660 000053EE 89DA                <1> 	mov	edx, ebx
   661 000053F0 C1EA16              <1> 	shr	edx, PAGE_D_SHIFT ; 22  (12+10)
   662 000053F3 C1E202              <1> 	shl 	edx, 2 ; offset to page directory (1024*4)
   663 000053F6 01C2                <1> 	add	edx, eax ; page directory address (physical)
   664 000053F8 8B02                <1> 	mov	eax, [edx]
   665 000053FA A801                <1> 	test	al, PDE_A_PRESENT ; page table is present or not !
   666 000053FC 751F                <1> 	jnz	short gpte_retn
   667 000053FE F9                  <1> 	stc
   668                              <1> gpde_retn:	
   669 000053FF C3                  <1> 	retn
   670                              <1> 
   671                              <1> get_pte:
   672                              <1> 		; Get present value of the relevant PTE
   673                              <1> 	; 29/07/2015
   674                              <1> 	; 20/07/2015
   675                              <1> 	; 18/04/2015
   676                              <1> 	; 12/04/2015
   677                              <1> 	; 10/10/2014 ; (Retro UNIX 386 v1 - beginning)
   678                              <1> 	;
   679                              <1> 	; INPUT ->
   680                              <1> 	;	EBX = virtual (linear) address
   681                              <1> 	;	EAX = page directory (physical) address
   682                              <1> 	; OUTPUT ->
   683                              <1> 	;	EDX = Page table entry address (if CF=0)
   684                              <1> 	;	      Page directory entry address (if CF=1)
   685                              <1> 	;            (Bit 0 value is 0 if PT is not present)
   686                              <1> 	;	EAX = Page table entry value (page address)
   687                              <1> 	;	CF = 1 -> PDE not present or invalid ? 
   688                              <1> 	; Modified Registers -> EAX, EDX
   689                              <1> 	;
   690 00005400 E8E9FFFFFF          <1> 	call 	get_pde
   691 00005405 72F8                <1> 	jc	short gpde_retn	; page table is not present
   692                              <1> 	;jnc	short gpte_1
   693                              <1> 	;retn
   694                              <1> ;gpte_1:
   695 00005407 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear lower 12 bits
   696 0000540B 89DA                <1> 	mov	edx, ebx
   697 0000540D C1EA0C              <1> 	shr	edx, PAGE_SHIFT ; 12
   698 00005410 81E2FF030000        <1> 	and	edx, PTE_MASK	; 03FFh
   699                              <1> 			 ; clear higher 10 bits (PD bits)
   700 00005416 C1E202              <1> 	shl	edx, 2 ; offset from start of page table (1024*4)
   701 00005419 01C2                <1> 	add	edx, eax
   702 0000541B 8B02                <1> 	mov	eax, [edx]
   703                              <1> gpte_retn:
   704 0000541D C3                  <1> 	retn
   705                              <1> 
   706                              <1> deallocate_page_dir:
   707                              <1> 	; 15/09/2015
   708                              <1> 	; 05/08/2015
   709                              <1> 	; 30/04/2015
   710                              <1> 	; 28/04/2015
   711                              <1> 	; 17/10/2014
   712                              <1> 	; 12/10/2014 (Retro UNIX 386 v1 - beginning)
   713                              <1> 	;
   714                              <1> 	; INPUT ->
   715                              <1> 	;	EAX = PHYSICAL ADDRESS OF THE PAGE DIRECTORY (CHILD)
   716                              <1> 	;	EBX = PHYSICAL ADDRESS OF THE PARENT'S PAGE DIRECTORY
   717                              <1> 	; OUTPUT ->
   718                              <1> 	;	All of page tables in the page directory
   719                              <1> 	;	and page dir's itself will be deallocated
   720                              <1> 	;	except 'read only' duplicated pages (will be converted
   721                              <1> 	;	to writable pages).
   722                              <1> 	;
   723                              <1> 	; Modified Registers -> EAX
   724                              <1> 	;
   725                              <1> 	;
   726 0000541E 56                  <1> 	push	esi
   727 0000541F 51                  <1> 	push	ecx
   728 00005420 50                  <1> 	push	eax
   729 00005421 89C6                <1> 	mov	esi, eax 
   730 00005423 31C9                <1> 	xor	ecx, ecx
   731                              <1> 	; The 1st PDE points to Kernel Page Table 0 (the 1st 4MB),
   732                              <1> 	; it must not be deallocated
   733 00005425 890E                <1> 	mov	[esi], ecx ; 0 ; clear PDE 0
   734                              <1> dapd_0:
   735 00005427 AD                  <1> 	lodsd
   736 00005428 A801                <1> 	test	al, PDE_A_PRESENT ; bit 0, present flag (must be 1)
   737 0000542A 7409                <1> 	jz	short dapd_1	
   738 0000542C 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
   739 00005430 E812000000          <1> 	call	deallocate_page_table			
   740                              <1> dapd_1:
   741 00005435 41                  <1> 	inc	ecx ; page directory entry index
   742 00005436 81F900040000        <1> 	cmp	ecx, PAGE_SIZE / 4 ; 1024
   743 0000543C 72E9                <1> 	jb	short dapd_0
   744                              <1> dapd_2:
   745 0000543E 58                  <1> 	pop	eax
   746 0000543F E87F000000          <1> 	call	deallocate_page	; deallocate the page dir's itself
   747 00005444 59                  <1> 	pop	ecx
   748 00005445 5E                  <1> 	pop	esi
   749 00005446 C3                  <1> 	retn
   750                              <1> 
   751                              <1> deallocate_page_table:
   752                              <1> 	; 12/07/2016
   753                              <1> 	; 19/09/2015
   754                              <1> 	; 15/09/2015
   755                              <1> 	; 05/08/2015
   756                              <1> 	; 30/04/2015
   757                              <1> 	; 28/04/2015
   758                              <1> 	; 24/10/2014
   759                              <1> 	; 23/10/2014
   760                              <1> 	; 12/10/2014 (Retro UNIX 386 v1 - beginning)
   761                              <1> 	;
   762                              <1> 	; INPUT ->
   763                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS OF THE PAGE TABLE
   764                              <1> 	;	EBX = PHYSICAL ADDRESS OF THE PARENT'S PAGE DIRECTORY
   765                              <1> 	;	(ECX = page directory entry index)
   766                              <1> 	; OUTPUT ->
   767                              <1> 	;	All of pages in the page table and page table's itself
   768                              <1> 	;	will be deallocated except 'read only' duplicated pages
   769                              <1> 	;	(will be converted to writable pages).
   770                              <1> 	;
   771                              <1> 	; Modified Registers -> EAX
   772                              <1> 	;
   773 00005447 56                  <1> 	push	esi
   774 00005448 57                  <1> 	push	edi
   775 00005449 52                  <1> 	push	edx
   776 0000544A 50                  <1> 	push	eax ; *
   777 0000544B 89C6                <1> 	mov	esi, eax 
   778 0000544D 31FF                <1> 	xor	edi, edi ; 0
   779                              <1> dapt_0:
   780 0000544F AD                  <1> 	lodsd
   781 00005450 A801                <1> 	test	al, PTE_A_PRESENT ; bit 0, present flag (must be 1)
   782 00005452 7441                <1> 	jz	short dapt_1
   783                              <1> 	;
   784 00005454 A802                <1> 	test	al, PTE_A_WRITE   ; bit 1, writable (r/w) flag
   785                              <1> 				  ; (must be 1)
   786 00005456 754C                <1> 	jnz	short dapt_3
   787                              <1> 	; Read only -duplicated- page (belongs to a parent or a child)
   788 00005458 66A90002            <1>         test    ax, PTE_DUPLICATED ; Was this page duplicated 
   789                              <1> 				   ; as child's page ?
   790 0000545C 7451                <1> 	jz	short dapt_4 ; Clear PTE but don't deallocate the page!
   791                              <1> 	; check the parent's PTE value is read only & same page or not.. 
   792                              <1> 	; ECX = page directory entry index (0-1023)
   793 0000545E 53                  <1> 	push	ebx
   794 0000545F 51                  <1> 	push	ecx
   795 00005460 66C1E102            <1> 	shl	cx, 2 ; *4 
   796 00005464 01CB                <1> 	add	ebx, ecx ; PDE offset (for the parent)
   797 00005466 8B0B                <1> 	mov	ecx, [ebx]
   798 00005468 F6C101              <1> 	test	cl, PDE_A_PRESENT ; present (valid) or not ?
   799 0000546B 7435                <1> 	jz	short dapt_2	; parent process does not use this page
   800 0000546D 6681E100F0          <1> 	and	cx, PDE_A_CLEAR ; 0F000h ; Clear attribute bits
   801                              <1> 	; EDI = page table entry index (0-1023)
   802 00005472 89FA                <1> 	mov	edx, edi 
   803 00005474 66C1E202            <1> 	shl	dx, 2 ; *4 
   804 00005478 01CA                <1> 	add	edx, ecx ; PTE offset (for the parent)
   805 0000547A 8B1A                <1> 	mov	ebx, [edx]
   806 0000547C F6C301              <1> 	test	bl, PTE_A_PRESENT ; present or not ?
   807 0000547F 7421                <1> 	jz	short dapt_2	; parent process does not use this page
   808 00005481 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; Clear attribute bits 
   809 00005485 6681E300F0          <1> 	and	bx, PTE_A_CLEAR ; 0F000h ; Clear attribute bits
   810 0000548A 39D8                <1> 	cmp	eax, ebx	; parent's and child's pages are same ?
   811 0000548C 7514                <1> 	jne	short dapt_2	; not same page
   812                              <1> 				; deallocate the child's page
   813 0000548E 800A02              <1>         or      byte [edx], PTE_A_WRITE ; convert to writable page (parent)
   814 00005491 59                  <1> 	pop	ecx
   815 00005492 5B                  <1> 	pop	ebx
   816 00005493 EB1A                <1> 	jmp	short dapt_4
   817                              <1> dapt_1:
   818 00005495 09C0                <1> 	or	eax, eax	; swapped page ?
   819 00005497 741D                <1> 	jz	short dapt_5	; no
   820                              <1> 				; yes
   821 00005499 D1E8                <1> 	shr	eax, 1
   822 0000549B E8CA040000          <1> 	call	unlink_swap_block ; Deallocate swapped page block
   823                              <1> 				  ; on the swap disk (or in file)
   824 000054A0 EB14                <1> 	jmp	short dapt_5
   825                              <1> dapt_2:
   826 000054A2 59                  <1> 	pop	ecx
   827 000054A3 5B                  <1> 	pop	ebx
   828                              <1> dapt_3:	
   829                              <1> 	; 12/07/2016
   830 000054A4 66A90004            <1> 	test	ax, PTE_SHARED ; shared or direct memory access indicator
   831 000054A8 7505                <1> 	jnz	short dapt_4   ; AVL bit 1 = 1, do not deallocate this page!
   832                              <1> 	;
   833                              <1> 	;and	ax, PTE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
   834 000054AA E814000000          <1> 	call	deallocate_page ; set the mem allocation bit of this page
   835                              <1> dapt_4:
   836 000054AF C746FC00000000      <1> 	mov	dword [esi-4], 0 ; clear/reset PTE (child, dupl. as parent)
   837                              <1> dapt_5:
   838 000054B6 47                  <1> 	inc	edi ; page table entry index
   839 000054B7 81FF00040000        <1> 	cmp	edi, PAGE_SIZE / 4 ; 1024
   840 000054BD 7290                <1> 	jb	short dapt_0
   841                              <1> 	;
   842 000054BF 58                  <1> 	pop	eax ; *
   843 000054C0 5A                  <1> 	pop	edx
   844 000054C1 5F                  <1> 	pop	edi	
   845 000054C2 5E                  <1> 	pop	esi
   846                              <1> 	;
   847                              <1> 	;call	deallocate_page	; deallocate the page table's itself
   848                              <1> 	;retn
   849                              <1> 
   850                              <1> deallocate_page:
   851                              <1> 	; 15/09/2015
   852                              <1> 	; 28/04/2015
   853                              <1> 	; 10/03/2015
   854                              <1> 	; 17/10/2014
   855                              <1> 	; 12/10/2014 (Retro UNIX 386 v1 - beginning)
   856                              <1> 	;
   857                              <1> 	; INPUT -> 
   858                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS OF THE ALLOCATED PAGE
   859                              <1> 	; OUTPUT ->
   860                              <1> 	;	[free_pages] is increased
   861                              <1> 	;	(corresponding MEMORY ALLOCATION TABLE bit is SET)
   862                              <1> 	;	CF = 1 if the page is already deallocated
   863                              <1> 	; 	       (or not allocated) before.  
   864                              <1> 	;
   865                              <1> 	; Modified Registers -> EAX
   866                              <1> 	;
   867 000054C3 53                  <1> 	push	ebx
   868 000054C4 52                  <1> 	push	edx
   869                              <1> 	;
   870 000054C5 C1E80C              <1> 	shr	eax, PAGE_SHIFT      ; shift physical address to 
   871                              <1> 				     ; 12 bits right
   872                              <1> 				     ; to get page number
   873 000054C8 89C2                <1> 	mov	edx, eax
   874                              <1> 	; 15/09/2015
   875 000054CA C1EA03              <1> 	shr	edx, 3		     ; to get offset to M.A.T.
   876                              <1> 				     ; (1 allocation bit = 1 page)
   877                              <1> 				     ; (1 allocation bytes = 8 pages)
   878 000054CD 80E2FC              <1> 	and	dl, 0FCh 	     ; clear lower 2 bits
   879                              <1> 				     ; (to get 32 bit position)			
   880                              <1> 	;
   881 000054D0 BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL   ; Memory Allocation Table address
   882 000054D5 01D3                <1> 	add	ebx, edx
   883 000054D7 83E01F              <1> 	and	eax, 1Fh	     ; lower 5 bits only
   884                              <1> 				     ; (allocation bit position)	 
   885 000054DA 3B15[8C5E0100]      <1> 	cmp 	edx, [next_page]     ; is the new free page address lower
   886                              <1> 				     ; than the address in 'next_page' ?
   887                              <1> 				     ; (next/first free page value)		
   888 000054E0 7306                <1> 	jnb	short dap_1	     ; no	
   889 000054E2 8915[8C5E0100]      <1> 	mov	[next_page], edx     ; yes
   890                              <1> dap_1:
   891 000054E8 0FAB03              <1> 	bts	[ebx], eax	     ; unlink/release/deallocate page
   892                              <1> 				     ; set relevant bit to 1.
   893                              <1> 				     ; set CF to the previous bit value	
   894                              <1> 	;cmc			     ; complement carry flag	
   895                              <1> 	;jc	short dap_2	     ; do not increase free_pages count
   896                              <1> 				     ; if the page is already deallocated
   897                              <1> 				     ; before.	
   898 000054EB FF05[885E0100]      <1>         inc     dword [free_pages]
   899                              <1> dap_2:
   900 000054F1 5A                  <1> 	pop	edx
   901 000054F2 5B                  <1> 	pop	ebx
   902 000054F3 C3                  <1> 	retn
   903                              <1> 
   904                              <1> ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
   905                              <1> ;;                                                              ;;
   906                              <1> ;; Copyright (C) KolibriOS team 2004-2012. All rights reserved. ;;
   907                              <1> ;; Distributed under terms of the GNU General Public License    ;;
   908                              <1> ;;                                                              ;;
   909                              <1> ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
   910                              <1> 
   911                              <1> ;;$Revision: 5057 $
   912                              <1> 
   913                              <1> 
   914                              <1> ;;align 4
   915                              <1> ;;proc alloc_page
   916                              <1> 
   917                              <1> ;;        pushfd
   918                              <1> ;;        cli
   919                              <1> ;;        push    ebx
   920                              <1> ;;;//-
   921                              <1> ;;        cmp     [pg_data.pages_free], 1
   922                              <1> ;;        jle     .out_of_memory
   923                              <1> ;;;//-
   924                              <1> ;;
   925                              <1> ;;        mov     ebx, [page_start]
   926                              <1> ;;        mov     ecx, [page_end]
   927                              <1> ;;.l1:
   928                              <1> ;;        bsf     eax, [ebx];
   929                              <1> ;;        jnz     .found
   930                              <1> ;;        add     ebx, 4
   931                              <1> ;;        cmp     ebx, ecx
   932                              <1> ;;        jb      .l1
   933                              <1> ;;        pop     ebx
   934                              <1> ;;        popfd
   935                              <1> ;;        xor     eax, eax
   936                              <1> ;;        ret
   937                              <1> ;;.found:
   938                              <1> ;;;//-
   939                              <1> ;;        dec     [pg_data.pages_free]
   940                              <1> ;;        jz      .out_of_memory
   941                              <1> ;;;//-
   942                              <1> ;;        btr     [ebx], eax
   943                              <1> ;;        mov     [page_start], ebx
   944                              <1> ;;        sub     ebx, sys_pgmap
   945                              <1> ;;        lea     eax, [eax+ebx*8]
   946                              <1> ;;        shl     eax, 12
   947                              <1> ;;;//-       dec [pg_data.pages_free]
   948                              <1> ;;        pop     ebx
   949                              <1> ;;        popfd
   950                              <1> ;;        ret
   951                              <1> ;;;//-
   952                              <1> ;;.out_of_memory:
   953                              <1> ;;        mov     [pg_data.pages_free], 1
   954                              <1> ;;        xor     eax, eax
   955                              <1> ;;        pop     ebx
   956                              <1> ;;        popfd
   957                              <1> ;;        ret
   958                              <1> ;;;//-
   959                              <1> ;;endp
   960                              <1> 
   961                              <1> duplicate_page_dir:
   962                              <1> 	; 21/09/2015
   963                              <1> 	; 31/08/2015
   964                              <1> 	; 20/07/2015
   965                              <1> 	; 28/04/2015
   966                              <1> 	; 27/04/2015
   967                              <1> 	; 18/04/2015
   968                              <1> 	; 12/04/2015
   969                              <1> 	; 18/10/2014
   970                              <1> 	; 16/10/2014 (Retro UNIX 386 v1 - beginning)
   971                              <1> 	;
   972                              <1> 	; INPUT -> 
   973                              <1> 	;	[u.pgdir] = PHYSICAL (real/flat) ADDRESS of the parent's
   974                              <1> 	;		    page directory.
   975                              <1> 	; OUTPUT ->
   976                              <1> 	;	EAX =  PHYSICAL (real/flat) ADDRESS of the child's
   977                              <1> 	;	       page directory.
   978                              <1> 	;	(New page directory with new page table entries.)
   979                              <1> 	;	(New page tables with read only copies of the parent's
   980                              <1> 	;	pages.)
   981                              <1> 	;	EAX = 0 -> Error (CF = 1)
   982                              <1> 	;
   983                              <1> 	; Modified Registers -> none (except EAX)
   984                              <1> 	;
   985 000054F4 E8ECFDFFFF          <1> 	call	allocate_page
   986 000054F9 723E                <1> 	jc	short dpd_err
   987                              <1> 	;
   988 000054FB 55                  <1> 	push	ebp ; 20/07/2015
   989 000054FC 56                  <1> 	push	esi
   990 000054FD 57                  <1> 	push	edi
   991 000054FE 53                  <1> 	push	ebx
   992 000054FF 51                  <1> 	push	ecx
   993 00005500 8B35[B8030300]      <1> 	mov	esi, [u.pgdir]
   994 00005506 89C7                <1> 	mov	edi, eax
   995 00005508 50                  <1> 	push	eax ; save child's page directory address
   996                              <1> 	; 31/08/2015
   997                              <1> 	; copy PDE 0 from the parent's page dir to the child's page dir
   998                              <1> 	; (use same system space for all user page tables) 
   999 00005509 A5                  <1> 	movsd
  1000 0000550A BD00004000          <1> 	mov	ebp, 1024*4096 ; pass the 1st 4MB (system space)
  1001 0000550F B9FF030000          <1> 	mov	ecx, (PAGE_SIZE / 4) - 1 ; 1023
  1002                              <1> dpd_0:	
  1003 00005514 AD                  <1> 	lodsd
  1004                              <1> 	;or	eax, eax
  1005                              <1>         ;jnz     short dpd_1
  1006 00005515 A801                <1> 	test	al, PDE_A_PRESENT ;  bit 0 =  1
  1007 00005517 7508                <1> 	jnz	short dpd_1
  1008                              <1>  	; 20/07/2015 (virtual address at the end of the page table)	
  1009 00005519 81C500004000        <1> 	add	ebp, 1024*4096 ; page size * PTE count
  1010 0000551F EB0F                <1> 	jmp	short dpd_2
  1011                              <1> dpd_1:	
  1012 00005521 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear attribute bits
  1013 00005525 89C3                <1> 	mov	ebx, eax
  1014                              <1> 	; EBX = Parent's page table address
  1015 00005527 E81F000000          <1> 	call	duplicate_page_table
  1016 0000552C 720C                <1> 	jc	short dpd_p_err
  1017                              <1> 	; EAX = Child's page table address
  1018 0000552E 0C07                <1> 	or	al, PDE_A_PRESENT + PDE_A_WRITE + PDE_A_USER
  1019                              <1> 			 ; set bit 0, bit 1 and bit 2 to 1
  1020                              <1> 			 ; (present, writable, user)
  1021                              <1> dpd_2:
  1022 00005530 AB                  <1> 	stosd
  1023 00005531 E2E1                <1> 	loop	dpd_0
  1024                              <1> 	;
  1025 00005533 58                  <1> 	pop	eax  ; restore child's page directory address
  1026                              <1> dpd_3:
  1027 00005534 59                  <1> 	pop	ecx
  1028 00005535 5B                  <1> 	pop	ebx
  1029 00005536 5F                  <1> 	pop	edi
  1030 00005537 5E                  <1> 	pop	esi
  1031 00005538 5D                  <1> 	pop	ebp ; 20/07/2015
  1032                              <1> dpd_err:
  1033 00005539 C3                  <1> 	retn
  1034                              <1> dpd_p_err:
  1035                              <1> 	; release the allocated pages missing (recover free space)
  1036 0000553A 58                  <1> 	pop	eax  ; the new page directory address (physical)
  1037 0000553B 8B1D[B8030300]      <1> 	mov	ebx, [u.pgdir] ; parent's page directory address 
  1038 00005541 E8D8FEFFFF          <1> 	call 	deallocate_page_dir
  1039 00005546 29C0                <1> 	sub	eax, eax ; 0
  1040 00005548 F9                  <1> 	stc
  1041 00005549 EBE9                <1> 	jmp	short dpd_3	
  1042                              <1> 
  1043                              <1> duplicate_page_table:
  1044                              <1> 	; 20/02/2017
  1045                              <1> 	; 21/09/2015
  1046                              <1> 	; 20/07/2015
  1047                              <1> 	; 05/05/2015
  1048                              <1> 	; 28/04/2015
  1049                              <1> 	; 27/04/2015
  1050                              <1> 	; 18/04/2015
  1051                              <1> 	; 18/10/2014
  1052                              <1> 	; 16/10/2014 (Retro UNIX 386 v1 - beginning)
  1053                              <1> 	;
  1054                              <1> 	; INPUT -> 
  1055                              <1> 	;	EBX = PHYSICAL (real/flat) ADDRESS of the parent's page table.
  1056                              <1> 	;       20/02/2017		 
  1057                              <1> 	;	EBP = Linear address of the page (from 'duplicate_page_dir')
  1058                              <1> 	;	      (Linear address = CORE + user's virtual address) 	
  1059                              <1> 	; OUTPUT ->
  1060                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS of the child's page table.
  1061                              <1> 	;	      (with 'read only' attribute of page table entries)
  1062                              <1> 	;	20/02/2017
  1063                              <1> 	;	EBP = Next linear page address (for 'duplicate_page_dir')
  1064                              <1> 	;	
  1065                              <1> 	;	CF = 1 -> error 
  1066                              <1> 	;
  1067                              <1> 	; Modified Registers -> EBP (except EAX)
  1068                              <1> 	;
  1069 0000554B E895FDFFFF          <1> 	call	allocate_page
  1070 00005550 726A                <1> 	jc	short dpt_err
  1071                              <1> 	;
  1072 00005552 50                  <1> 	push	eax ; *
  1073 00005553 56                  <1> 	push	esi
  1074 00005554 57                  <1> 	push	edi
  1075 00005555 52                  <1> 	push	edx
  1076 00005556 51                  <1> 	push	ecx
  1077                              <1> 	;
  1078 00005557 89DE                <1> 	mov	esi, ebx
  1079 00005559 89C7                <1> 	mov	edi, eax
  1080 0000555B 89C2                <1> 	mov	edx, eax
  1081 0000555D 81C200100000        <1> 	add	edx, PAGE_SIZE 	
  1082                              <1> dpt_0:
  1083 00005563 AD                  <1> 	lodsd
  1084 00005564 21C0                <1> 	and	eax, eax
  1085 00005566 7444                <1> 	jz	short dpt_3
  1086 00005568 A801                <1> 	test	al, PTE_A_PRESENT ;  bit 0 =  1
  1087 0000556A 7507                <1> 	jnz	short dpt_1
  1088                              <1> 	; 20/07/2015
  1089                              <1> 	; ebp = virtual (linear) address of the memory page
  1090 0000556C E83F050000          <1> 	call	reload_page ; 28/04/2015
  1091 00005571 7244                <1> 	jc	short dpt_p_err
  1092                              <1> dpt_1:
  1093                              <1> 	; 21/09/2015
  1094 00005573 89C1                <1> 	mov	ecx, eax
  1095 00005575 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear attribute bits
  1096 00005579 F6C102              <1> 	test	cl, PTE_A_WRITE ; writable page ?
  1097 0000557C 7525                <1> 	jnz	short dpt_2
  1098                              <1> 	; Read only (parent) page
  1099                              <1> 	; 	- there is a third process which uses this page -
  1100                              <1> 	; Allocate a new page for the child process
  1101 0000557E E862FDFFFF          <1> 	call	allocate_page
  1102 00005583 7232                <1> 	jc	short dpt_p_err
  1103 00005585 57                  <1> 	push	edi
  1104 00005586 56                  <1> 	push	esi
  1105 00005587 89CE                <1> 	mov	esi, ecx
  1106 00005589 89C7                <1> 	mov	edi, eax
  1107 0000558B B900040000          <1> 	mov	ecx, PAGE_SIZE/4
  1108 00005590 F3A5                <1> 	rep	movsd	; copy page (4096 bytes)
  1109 00005592 5E                  <1> 	pop	esi
  1110 00005593 5F                  <1> 	pop	edi
  1111                              <1> 	; 
  1112 00005594 53                  <1> 	push	ebx
  1113 00005595 50                  <1> 	push	eax
  1114                              <1> 	; 20/07/2015
  1115 00005596 89EB                <1> 	mov	ebx, ebp
  1116                              <1> 	; ebx = virtual (linear) address of the memory page
  1117 00005598 E887030000          <1> 	call	add_to_swap_queue
  1118 0000559D 58                  <1> 	pop	eax
  1119 0000559E 5B                  <1> 	pop	ebx
  1120                              <1> 	; 21/09/2015
  1121 0000559F 0C07                <1> 	or	al, PTE_A_USER+PTE_A_WRITE+PTE_A_PRESENT 
  1122                              <1> 		; user + writable + present page
  1123 000055A1 EB09                <1> 	jmp	short dpt_3
  1124                              <1> dpt_2:
  1125                              <1> 	;or	ax, PTE_A_USER+PTE_A_PRESENT 
  1126 000055A3 0C05                <1> 	or	al, PTE_A_USER+PTE_A_PRESENT 
  1127                              <1> 		    ; (read only page!)
  1128 000055A5 8946FC              <1> 	mov	[esi-4], eax ; update parent's PTE
  1129 000055A8 660D0002            <1> 	or      ax, PTE_DUPLICATED  ; (read only page & duplicated PTE!)
  1130                              <1> dpt_3:
  1131 000055AC AB                  <1> 	stosd  ; EDI points to child's PTE  	 
  1132                              <1> 	;
  1133 000055AD 81C500100000        <1> 	add	ebp, 4096 ; 20/07/2015 (next page)
  1134                              <1> 	;
  1135 000055B3 39D7                <1> 	cmp	edi, edx
  1136 000055B5 72AC                <1> 	jb	short dpt_0
  1137                              <1> dpt_p_err:
  1138 000055B7 59                  <1> 	pop	ecx
  1139 000055B8 5A                  <1> 	pop	edx
  1140 000055B9 5F                  <1> 	pop	edi
  1141 000055BA 5E                  <1> 	pop	esi
  1142 000055BB 58                  <1> 	pop	eax ; *
  1143                              <1> dpt_err:
  1144 000055BC C3                  <1> 	retn
  1145                              <1> 
  1146                              <1> page_fault_handler:	; CPU EXCEPTION 0Eh (14) : Page Fault !
  1147                              <1> 	; 21/09/2015
  1148                              <1> 	; 19/09/2015
  1149                              <1> 	; 17/09/2015
  1150                              <1> 	; 28/08/2015
  1151                              <1> 	; 20/07/2015
  1152                              <1> 	; 28/06/2015
  1153                              <1> 	; 03/05/2015
  1154                              <1> 	; 30/04/2015
  1155                              <1> 	; 18/04/2015
  1156                              <1> 	; 12/04/2015
  1157                              <1> 	; 30/10/2014
  1158                              <1> 	; 11/09/2014
  1159                              <1> 	; 10/09/2014 (Retro UNIX 386 v1 - beginning)
  1160                              <1> 	;
  1161                              <1> 	; Note: This is not an interrupt/exception handler.
  1162                              <1> 	;	This is a 'page fault remedy' subroutine 
  1163                              <1> 	;	which will be called by standard/uniform
  1164                              <1> 	;	exception handler.
  1165                              <1> 	;
  1166                              <1> 	; INPUT -> 
  1167                              <1> 	;	[error_code] = 32 bit ERROR CODE (lower 5 bits are valid)
  1168                              <1> 	;
  1169                              <1> 	;	cr2 = the virtual (linear) address 
  1170                              <1> 	;	      which has caused to page fault (19/09/2015)
  1171                              <1> 	;
  1172                              <1> 	; OUTPUT ->
  1173                              <1> 	;	(corresponding PAGE TABLE ENTRY is mapped/set)
  1174                              <1> 	;	EAX = 0 -> no error
  1175                              <1> 	;	EAX > 0 -> error code in EAX (also CF = 1)
  1176                              <1> 	;
  1177                              <1> 	; Modified Registers -> none (except EAX)
  1178                              <1> 	;	
  1179                              <1>         ;
  1180                              <1>         ; ERROR CODE:
  1181                              <1> 	;	 31  .....	4   3	2   1	0
  1182                              <1> 	;	+---+-- --+---+---+---+---+---+---+
  1183                              <1> 	;	|   Reserved  | I | R | U | W | P |
  1184                              <1> 	;	+---+-- --+---+---+---+---+---+---+
  1185                              <1> 	;
  1186                              <1> 	; P : PRESENT -	When set, the page fault was caused by 
  1187                              <1>     	;		a page-protection violation. When not set,
  1188                              <1> 	;		it was caused by a non-present page.
  1189                              <1> 	; W : WRITE   -	When set, the page fault was caused by
  1190                              <1> 	;		a page write. When not set, it was caused
  1191                              <1> 	;		by a page read.
  1192                              <1> 	; U : USER    -	When set, the page fault was caused 
  1193                              <1> 	;		while CPL = 3. 
  1194                              <1> 	;		This does not necessarily mean that
  1195                              <1> 	;		the page fault was a privilege violation.
  1196                              <1> 	; R : RESERVD -	When set, the page fault was caused by
  1197                              <1> 	;     WRITE	reading a 1 in a reserved field.
  1198                              <1> 	; I : INSTRUC -	When set, the page fault was caused by
  1199                              <1> 	;     FETCH	an instruction fetch
  1200                              <1> 	;
  1201                              <1> 	;; x86 (32 bit) VIRTUAL ADDRESS TRANSLATION
  1202                              <1> 	;  31               22                  12 11                    0
  1203                              <1> 	; +-------------------+-------------------+-----------------------+
  1204                              <1>        	; | PAGE DIR. ENTRY # | PAGE TAB. ENTRY # |        OFFSET         |
  1205                              <1>        	; +-------------------+-------------------+-----------------------+
  1206                              <1> 	;
  1207                              <1> 
  1208                              <1> 	;; CR3 REGISTER (Control Register 3)
  1209                              <1> 	;  31                                   12             5 4 3 2   0
  1210                              <1> 	; +---------------------------------------+-------------+---+-----+
  1211                              <1>       	; |                                       |  		|P|P|     |
  1212                              <1>       	; |   PAGE DIRECTORY TABLE BASE ADDRESS   |  reserved	|C|W|rsvrd|
  1213                              <1>       	; |                                       | 		|D|T|     |
  1214                              <1>    	; +---------------------------------------+-------------+---+-----+
  1215                              <1> 	;
  1216                              <1> 	;	PWT    - WRITE THROUGH
  1217                              <1> 	;	PCD    - CACHE DISABLE		
  1218                              <1> 	;
  1219                              <1> 	;
  1220                              <1> 	;; x86 PAGE DIRECTORY ENTRY (4 KByte Page)
  1221                              <1> 	;  31                                   12 11  9 8 7 6 5 4 3 2 1 0
  1222                              <1> 	; +---------------------------------------+-----+---+-+-+---+-+-+-+
  1223                              <1>       	; |                                       |     | | | | |P|P|U|R| |
  1224                              <1>       	; |     PAGE TABLE BASE ADDRESS 31..12    | AVL |G|0|D|A|C|W|/|/|P|
  1225                              <1>       	; |                                       |     | | | | |D|T|S|W| |
  1226                              <1>    	; +---------------------------------------+-----+---+-+-+---+-+-+-+
  1227                              <1> 	;
  1228                              <1>         ;       P      - PRESENT
  1229                              <1>         ;       R/W    - READ/WRITE
  1230                              <1>         ;       U/S    - USER/SUPERVISOR
  1231                              <1> 	;	PWT    - WRITE THROUGH
  1232                              <1> 	;	PCD    - CACHE DISABLE	
  1233                              <1> 	;	A      - ACCESSED	
  1234                              <1>         ;       D      - DIRTY (IGNORED)
  1235                              <1> 	;	PAT    - PAGE ATTRIBUTE TABLE INDEX (CACHE BEHAVIOR)
  1236                              <1> 	;	G      - GLOBAL	(IGNORED) 
  1237                              <1>         ;       AVL    - AVAILABLE FOR SYSTEMS PROGRAMMER USE
  1238                              <1> 	;
  1239                              <1> 	;
  1240                              <1> 	;; x86 PAGE TABLE ENTRY (4 KByte Page)
  1241                              <1> 	;  31                                   12 11  9 8 7 6 5 4 3 2 1 0
  1242                              <1> 	; +---------------------------------------+-----+---+-+-+---+-+-+-+
  1243                              <1>       	; |                                       |     | |P| | |P|P|U|R| |
  1244                              <1>       	; |     PAGE FRAME BASE ADDRESS 31..12    | AVL |G|A|D|A|C|W|/|/|P|
  1245                              <1>       	; |                                       |     | |T| | |D|T|S|W| |
  1246                              <1>    	; +---------------------------------------+-----+---+-+-+---+-+-+-+
  1247                              <1> 	;
  1248                              <1>         ;       P      - PRESENT
  1249                              <1>         ;       R/W    - READ/WRITE
  1250                              <1>         ;       U/S    - USER/SUPERVISOR
  1251                              <1> 	;	PWT    - WRITE THROUGH
  1252                              <1> 	;	PCD    - CACHE DISABLE	
  1253                              <1> 	;	A      - ACCESSED	
  1254                              <1>         ;       D      - DIRTY
  1255                              <1> 	;	PAT    - PAGE ATTRIBUTE TABLE INDEX (CACHE BEHAVIOR)
  1256                              <1> 	;	G      - GLOBAL	 
  1257                              <1>         ;       AVL    - AVAILABLE FOR SYSTEMS PROGRAMMER USE
  1258                              <1> 	;
  1259                              <1> 	;
  1260                              <1> 	;; 80386 PAGE TABLE ENTRY (4 KByte Page)
  1261                              <1> 	;  31                                   12 11  9 8 7 6 5 4 3 2 1 0
  1262                              <1> 	; +---------------------------------------+-----+-+-+-+-+---+-+-+-+
  1263                              <1>       	; |                                       |     | | | | | | |U|R| |
  1264                              <1>       	; |     PAGE FRAME BASE ADDRESS 31..12    | AVL |0|0|D|A|0|0|/|/|P|
  1265                              <1>       	; |                                       |     | | | | | | |S|W| |
  1266                              <1>       	; +---------------------------------------+-----+-+-+-+-+---+-+-+-+
  1267                              <1> 	;
  1268                              <1>         ;       P      - PRESENT
  1269                              <1>         ;       R/W    - READ/WRITE
  1270                              <1>         ;       U/S    - USER/SUPERVISOR
  1271                              <1>         ;       D      - DIRTY
  1272                              <1>         ;       AVL    - AVAILABLE FOR SYSTEMS PROGRAMMER USE
  1273                              <1> 	;
  1274                              <1>         ;       NOTE: 0 INDICATES INTEL RESERVED. DO NOT DEFINE.
  1275                              <1> 	;
  1276                              <1> 	;
  1277                              <1> 	;; Invalid Page Table Entry
  1278                              <1> 	; 31                                                           1 0
  1279                              <1>       	; +-------------------------------------------------------------+-+
  1280                              <1>       	; |                                                             | |
  1281                              <1>       	; |                          AVAILABLE                          |0|
  1282                              <1>       	; |                                                             | |
  1283                              <1>       	; +-------------------------------------------------------------+-+
  1284                              <1> 	;
  1285                              <1> 
  1286 000055BD 53                  <1> 	push	ebx
  1287 000055BE 52                  <1> 	push	edx
  1288 000055BF 51                  <1> 	push	ecx
  1289                              <1> 	;
  1290                              <1> 	; 21/09/2015 (debugging)
  1291 000055C0 FF05[CC030300]      <1> 	inc	dword [u.pfcount] ; page fault count for running process
  1292 000055C6 FF05[80050300]      <1> 	inc	dword [PF_Count] ; total page fault count	
  1293                              <1> 	; 28/06/2015
  1294                              <1> 	;mov	edx, [error_code] ; Lower 5 bits are valid
  1295 000055CC 8A15[78050300]      <1> 	mov	dl, [error_code]
  1296                              <1> 	;
  1297 000055D2 F6C201              <1> 	test	dl, 1	; page fault was caused by a non-present page
  1298                              <1> 			; sign
  1299 000055D5 7422                <1> 	jz	short pfh_alloc_np
  1300                              <1> 	; 
  1301                              <1> 	; If it is not a 'write on read only page' type page fault
  1302                              <1> 	; major page fault error with minor reason must be returned without 
  1303                              <1> 	; fixing the problem. 'sys_exit with error' will be needed
  1304                              <1> 	; after return here!
  1305                              <1> 	; Page fault will be remedied, by copying page contents
  1306                              <1> 	; to newly allocated page with write permission;
  1307                              <1> 	; sys_fork -> sys_exec -> copy on write, demand paging method is 
  1308                              <1> 	; used for working with minimum possible memory usage. 
  1309                              <1> 	; sys_fork will duplicate page directory and tables of parent  
  1310                              <1> 	; process with 'read only' flag. If the child process attempts to
  1311                              <1> 	; write on these read only pages, page fault will be directed here
  1312                              <1> 	; for allocating a new page with same data/content. 
  1313                              <1> 	;
  1314                              <1> 	; IMPORTANT : Retro UNIX 386 v1 (and SINGLIX and TR-DOS)
  1315                              <1> 	; will not force to separate CODE and DATA space 
  1316                              <1> 	; in a process/program... 
  1317                              <1> 	; CODE segment/section may contain DATA!
  1318                              <1> 	; It is flat, smoth and simplest programming method already as in 
  1319                              <1> 	; Retro UNIX 8086 v1 and MS-DOS programs.
  1320                              <1> 	;	
  1321 000055D7 F6C202              <1> 	test	dl, 2	; page fault was caused by a page write
  1322                              <1> 			; sign
  1323 000055DA 0F84AB000000        <1>         jz      pfh_p_err
  1324                              <1> 	; 31/08/2015
  1325 000055E0 F6C204              <1> 	test	dl, 4	; page fault was caused while CPL = 3 (user mode)
  1326                              <1> 			; sign.  (U+W+P = 4+2+1 = 7)
  1327 000055E3 0F84A2000000        <1>         jz	pfh_pv_err
  1328                              <1> 	;
  1329                              <1> 	; make a new page and copy the parent's page content
  1330                              <1> 	; as the child's new page content
  1331                              <1> 	;
  1332 000055E9 0F20D3              <1> 	mov	ebx, cr2 ; CR2 contains the linear address 
  1333                              <1> 			 ; which has caused to page fault
  1334 000055EC E8A2000000          <1> 	call 	copy_page
  1335 000055F1 0F828D000000        <1>         jc      pfh_im_err ; insufficient memory
  1336                              <1> 	;
  1337 000055F7 EB7D                <1>         jmp     pfh_cpp_ok
  1338                              <1> 	;
  1339                              <1> pfh_alloc_np:
  1340 000055F9 E8E7FCFFFF          <1> 	call	allocate_page	; (allocate a new page)
  1341 000055FE 0F8280000000        <1>         jc      pfh_im_err	; 'insufficient memory' error
  1342                              <1> pfh_chk_cpl:
  1343                              <1> 	; EAX = Physical (base) address of the allocated (new) page
  1344                              <1> 		; (Lower 12 bits are ZERO, because 
  1345                              <1> 		;	the address is on a page boundary)
  1346 00005604 80E204              <1> 	and	dl, 4	; CPL = 3 ?
  1347 00005607 7505                <1> 	jnz	short pfh_um
  1348                              <1> 			; Page fault handler for kernel/system mode (CPL=0)		
  1349 00005609 0F20DB              <1> 	mov	ebx, cr3 ; CR3 (Control Register 3) contains physical address
  1350                              <1> 			 ; of the current/active page directory
  1351                              <1> 			 ; (Always kernel/system mode page directory, here!)
  1352                              <1> 			 ; Note: Lower 12 bits are 0. (page boundary)
  1353 0000560C EB06                <1> 	jmp	short pfh_get_pde
  1354                              <1> 	;
  1355                              <1> pfh_um:			; Page fault handler for user/appl. mode (CPL=3)
  1356 0000560E 8B1D[B8030300]      <1>  	mov	ebx, [u.pgdir] ; Page directory of current/active process
  1357                              <1> 			; Physical address of the USER's page directory
  1358                              <1> 			; Note: Lower 12 bits are 0. (page boundary)
  1359                              <1> pfh_get_pde:
  1360 00005614 80CA03              <1> 	or	dl, 3	; USER + WRITE + PRESENT or SYSTEM + WRITE + PRESENT
  1361 00005617 0F20D1              <1> 	mov	ecx, cr2 ; CR2 contains the virtual address 
  1362                              <1> 			 ; which has been caused to page fault
  1363                              <1> 			 ;
  1364 0000561A C1E914              <1> 	shr	ecx, 20	 ; shift 20 bits right
  1365 0000561D 80E1FC              <1> 	and	cl, 0FCh ; mask lower 2 bits to get PDE offset		
  1366                              <1> 	;
  1367 00005620 01CB                <1> 	add	ebx, ecx ; now, EBX points to the relevant page dir entry 
  1368 00005622 8B0B                <1> 	mov	ecx, [ebx] ; physical (base) address of the page table 	
  1369 00005624 F6C101              <1> 	test	cl, 1	 ; check bit 0 is set (1) or not (0).
  1370 00005627 740B                <1> 	jz	short pfh_set_pde ; Page directory entry is not valid,
  1371                              <1> 			  	  ; set/validate page directory entry
  1372 00005629 6681E100F0          <1> 	and	cx, PDE_A_CLEAR ; 0F000h ; Clear attribute bits
  1373 0000562E 89CB                <1> 	mov	ebx, ecx ; Physical address of the page table
  1374 00005630 89C1                <1> 	mov	ecx, eax ; new page address (physical) 	
  1375 00005632 EB16                <1> 	jmp	short pfh_get_pte
  1376                              <1> pfh_set_pde:
  1377                              <1> 	;; NOTE: Page directories and page tables never be swapped out!
  1378                              <1> 	;;	 (So, we know this PDE is empty or invalid)
  1379                              <1> 	;
  1380 00005634 08D0                <1> 	or	al, dl	 ; lower 3 bits are used as U/S, R/W, P flags
  1381 00005636 8903                <1> 	mov	[ebx], eax ; Let's put the new page directory entry here !
  1382 00005638 30C0                <1> 	xor	al, al	 ; clear lower (3..8) bits
  1383 0000563A 89C3                <1> 	mov	ebx, eax
  1384 0000563C E8A4FCFFFF          <1> 	call	allocate_page	 ; (allocate a new page)
  1385 00005641 7241                <1> 	jc	short pfh_im_err   ; 'insufficient memory' error
  1386                              <1> pfh_spde_1:
  1387                              <1> 	; EAX = Physical (base) address of the allocated (new) page
  1388 00005643 89C1                <1> 	mov	ecx, eax
  1389 00005645 E815FDFFFF          <1> 	call	clear_page ; Clear page content
  1390                              <1> pfh_get_pte:
  1391 0000564A 0F20D0              <1> 	mov	eax, cr2 ; virtual address
  1392                              <1> 			 ; which has been caused to page fault
  1393 0000564D 89C7                <1> 	mov	edi, eax ; 20/07/2015
  1394 0000564F C1E80C              <1> 	shr	eax, 12	 ; shift 12 bit right to get 
  1395                              <1> 			 ; higher 20 bits of the page fault address 
  1396 00005652 25FF030000          <1> 	and	eax, 3FFh ; mask PDE# bits, the result is PTE# (0 to 1023)
  1397 00005657 C1E002              <1> 	shl	eax, 2	; shift 2 bits left to get PTE offset
  1398 0000565A 01C3                <1> 	add	ebx, eax ; now, EBX points to the relevant page table entry 
  1399 0000565C 8B03                <1> 	mov	eax, [ebx] ; get previous value of pte
  1400                              <1> 		; bit 0 of EAX is always 0 (otherwise we would not be here)
  1401 0000565E 21C0                <1> 	and	eax, eax
  1402 00005660 7410                <1> 	jz	short pfh_gpte_1
  1403                              <1> 	; 20/07/2015
  1404 00005662 87D9                <1> 	xchg	ebx, ecx ; new page address (physical)
  1405 00005664 55                  <1> 	push	ebp ; 20/07/2015
  1406 00005665 0F20D5              <1> 	mov	ebp, cr2
  1407                              <1> 		; ECX = physical address of the page table entry
  1408                              <1> 		; EBX = Memory page address (physical!)
  1409                              <1> 		; EAX = Swap disk (offset) address
  1410                              <1> 		; EBP = virtual address (page fault address)
  1411 00005668 E8B7000000          <1> 	call	swap_in
  1412 0000566D 5D                  <1> 	pop	ebp
  1413 0000566E 7210                <1> 	jc      short pfh_err_retn
  1414 00005670 87CB                <1> 	xchg	ecx, ebx
  1415                              <1> 		; EBX = physical address of the page table entry
  1416                              <1> 		; ECX = new page
  1417                              <1> pfh_gpte_1:
  1418 00005672 08D1                <1> 	or	cl, dl	; lower 3 bits are used as U/S, R/W, P flags
  1419 00005674 890B                <1> 	mov	[ebx], ecx ; Let's put the new page table entry here !
  1420                              <1> pfh_cpp_ok:
  1421                              <1> 	; 20/07/2015
  1422 00005676 0F20D3              <1> 	mov	ebx, cr2
  1423 00005679 E8A6020000          <1> 	call 	add_to_swap_queue
  1424                              <1> 	;
  1425                              <1> 	; The new PTE (which contains the new page) will be added to 
  1426                              <1> 	; the swap queue, here. 
  1427                              <1> 	; (Later, if memory will become insufficient, 
  1428                              <1> 	; one page will be swapped out which is at the head of 
  1429                              <1> 	; the swap queue by using FIFO and access check methods.)
  1430                              <1> 	;
  1431 0000567E 31C0                <1> 	xor	eax, eax  ; 0
  1432                              <1> 	;
  1433                              <1> pfh_err_retn:
  1434 00005680 59                  <1> 	pop	ecx
  1435 00005681 5A                  <1> 	pop	edx
  1436 00005682 5B                  <1> 	pop	ebx
  1437 00005683 C3                  <1> 	retn 
  1438                              <1> 	
  1439                              <1> pfh_im_err:
  1440 00005684 B8E4000000          <1> 	mov	eax, ERR_MAJOR_PF + ERR_MINOR_IM ; Error code in AX
  1441                              <1> 			; Major (Primary) Error: Page Fault
  1442                              <1> 			; Minor (Secondary) Error: Insufficient Memory !
  1443 00005689 EBF5                <1> 	jmp	short pfh_err_retn
  1444                              <1> 
  1445                              <1> 
  1446                              <1> pfh_p_err: ; 09/03/2015
  1447                              <1> pfh_pv_err:
  1448                              <1> 	; Page fault was caused by a protection-violation
  1449 0000568B B8E6000000          <1> 	mov	eax, ERR_MAJOR_PF + ERR_MINOR_PV ; Error code in AX
  1450                              <1> 			; Major (Primary) Error: Page Fault
  1451                              <1> 			; Minor (Secondary) Error: Protection violation !
  1452 00005690 F9                  <1> 	stc
  1453 00005691 EBED                <1> 	jmp	short pfh_err_retn
  1454                              <1> 
  1455                              <1> copy_page:
  1456                              <1> 	; 22/09/2015
  1457                              <1> 	; 21/09/2015
  1458                              <1> 	; 19/09/2015
  1459                              <1> 	; 07/09/2015
  1460                              <1> 	; 31/08/2015
  1461                              <1> 	; 20/07/2015
  1462                              <1> 	; 05/05/2015
  1463                              <1> 	; 03/05/2015
  1464                              <1> 	; 18/04/2015
  1465                              <1> 	; 12/04/2015
  1466                              <1> 	; 30/10/2014
  1467                              <1> 	; 18/10/2014 (Retro UNIX 386 v1 - beginning)
  1468                              <1> 	;
  1469                              <1> 	; INPUT -> 
  1470                              <1> 	;	EBX = Virtual (linear) address of source page
  1471                              <1> 	;	     (Page fault address)
  1472                              <1> 	; OUTPUT ->
  1473                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS OF THE ALLOCATED PAGE
  1474                              <1> 	;	(corresponding PAGE TABLE ENTRY is mapped/set)
  1475                              <1> 	;	EAX = 0 (CF = 1) 
  1476                              <1> 	;		if there is not a free page to be allocated
  1477                              <1> 	;	(page content of the source page will be copied
  1478                              <1> 	;	onto the target/new page) 	
  1479                              <1> 	;
  1480                              <1> 	; Modified Registers -> ecx, ebx (except EAX)
  1481                              <1> 	;	
  1482 00005693 56                  <1> 	push	esi
  1483 00005694 57                  <1> 	push	edi
  1484                              <1> 	;push	ebx
  1485                              <1> 	;push	ecx
  1486 00005695 31F6                <1> 	xor 	esi, esi
  1487 00005697 C1EB0C              <1> 	shr	ebx, 12 ; shift 12 bits right to get PDE & PTE numbers
  1488 0000569A 89D9                <1> 	mov	ecx, ebx ; save page fault address (as 12 bit shifted)
  1489 0000569C C1EB08              <1> 	shr	ebx, 8	 ; shift 8 bits right and then
  1490 0000569F 80E3FC              <1> 	and	bl, 0FCh ; mask lower 2 bits to get PDE offset	
  1491 000056A2 89DF                <1> 	mov 	edi, ebx ; save it for the parent of current process
  1492 000056A4 031D[B8030300]      <1> 	add	ebx, [u.pgdir] ; EBX points to the relevant page dir entry 
  1493 000056AA 8B03                <1> 	mov	eax, [ebx] ; physical (base) address of the page table
  1494 000056AC 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear attribute bits 	
  1495 000056B0 89CB                <1> 	mov	ebx, ecx   ; (restore higher 20 bits of page fault address)
  1496 000056B2 81E3FF030000        <1> 	and	ebx, 3FFh  ; mask PDE# bits, the result is PTE# (0 to 1023)
  1497 000056B8 66C1E302            <1> 	shl	bx, 2	   ; shift 2 bits left to get PTE offset
  1498 000056BC 01C3                <1> 	add	ebx, eax   ; EBX points to the relevant page table entry 
  1499                              <1> 	; 07/09/2015
  1500 000056BE 66F7030002          <1>         test    word [ebx], PTE_DUPLICATED ; (Does current process share this
  1501                              <1> 				     ; read only page as a child process?)	
  1502 000056C3 7509                <1> 	jnz	short cpp_0 ; yes
  1503 000056C5 8B0B                <1> 	mov	ecx, [ebx] ; PTE value
  1504 000056C7 6681E100F0          <1> 	and	cx, PTE_A_CLEAR ; 0F000h  ; clear page attributes
  1505 000056CC EB32                <1> 	jmp	short cpp_1
  1506                              <1> cpp_0:
  1507 000056CE 89FE                <1> 	mov	esi, edi
  1508 000056D0 0335[BC030300]      <1> 	add	esi, [u.ppgdir] ; the parent's page directory entry
  1509 000056D6 8B06                <1> 	mov	eax, [esi] ; physical (base) address of the page table
  1510 000056D8 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear attribute bits
  1511 000056DC 89CE                <1> 	mov	esi, ecx   ; (restore higher 20 bits of page fault address)	
  1512 000056DE 81E6FF030000        <1> 	and	esi, 3FFh  ; mask PDE# bits, the result is PTE# (0 to 1023)
  1513 000056E4 66C1E602            <1> 	shl	si, 2	   ; shift 2 bits left to get PTE offset
  1514 000056E8 01C6                <1> 	add	esi, eax   ; EDX points to the relevant page table entry  	
  1515 000056EA 8B0E                <1> 	mov	ecx, [esi] ; PTE value of the parent process
  1516                              <1> 	; 21/09/2015
  1517 000056EC 8B03                <1> 	mov	eax, [ebx] ; PTE value of the child process
  1518 000056EE 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear page attributes	
  1519                              <1> 	;
  1520 000056F2 F6C101              <1> 	test	cl, PTE_A_PRESENT ; is it a present/valid page ?
  1521 000056F5 7424                <1> 	jz	short cpp_3 ; the parent's page is not same page  	
  1522                              <1> 	;
  1523 000056F7 6681E100F0          <1> 	and	cx, PTE_A_CLEAR ; 0F000h ; clear page attributes
  1524 000056FC 39C8                <1> 	cmp	eax, ecx   ; Same page?	
  1525 000056FE 751B                <1> 	jne	short cpp_3 ; Parent page and child page are not same 
  1526                              <1> 			    ; Convert child's page to writable page
  1527                              <1> cpp_1:
  1528 00005700 E8E0FBFFFF          <1> 	call	allocate_page
  1529 00005705 721A                <1> 	jc	short cpp_4 ; 'insufficient memory' error
  1530 00005707 21F6                <1> 	and	esi, esi    ; check ESI is valid or not
  1531 00005709 7405                <1> 	jz	short cpp_2
  1532                              <1> 		; Convert read only page to writable page 
  1533                              <1> 		;(for the parent of the current process)
  1534                              <1> 	;and	word [esi], PTE_A_CLEAR ; 0F000h
  1535                              <1> 	; 22/09/2015
  1536 0000570B 890E                <1> 	mov	[esi], ecx
  1537 0000570D 800E07              <1> 	or	byte [esi], PTE_A_PRESENT + PTE_A_WRITE + PTE_A_USER
  1538                              <1> 				 ; 1+2+4 = 7
  1539                              <1> cpp_2:
  1540 00005710 89C7                <1> 	mov	edi, eax ; new page address of the child process
  1541                              <1> 	; 07/09/2015
  1542 00005712 89CE                <1> 	mov	esi, ecx ; the page address of the parent process
  1543 00005714 B900040000          <1> 	mov	ecx, PAGE_SIZE / 4
  1544 00005719 F3A5                <1> 	rep	movsd ; 31/08/2015
  1545                              <1> cpp_3:		
  1546 0000571B 0C07                <1> 	or	al, PTE_A_PRESENT + PTE_A_WRITE + PTE_A_USER ; 1+2+4 = 7
  1547 0000571D 8903                <1> 	mov	[ebx], eax ; Update PTE
  1548 0000571F 28C0                <1> 	sub	al, al ; clear attributes
  1549                              <1> cpp_4:
  1550                              <1> 	;pop	ecx
  1551                              <1> 	;pop	ebx
  1552 00005721 5F                  <1> 	pop	edi
  1553 00005722 5E                  <1> 	pop	esi
  1554 00005723 C3                  <1> 	retn
  1555                              <1> 
  1556                              <1> ;; 28/04/2015
  1557                              <1> ;; 24/10/2014
  1558                              <1> ;; 21/10/2014 (Retro UNIX 386 v1 - beginning)
  1559                              <1> ;; SWAP_PAGE_QUEUE (4096 bytes)
  1560                              <1> ;;
  1561                              <1> ;;   0000   0001   0002   0003   ....   1020   1021   1022   1023	
  1562                              <1> ;; +------+------+------+------+-    -+------+------+------+------+
  1563                              <1> ;; |  pg1 |  pg2 |  pg3 |  pg4 | .... |pg1021|pg1022|pg1023|pg1024|
  1564                              <1> ;; +------+------+------+------+-    -+------+------+------+------+    
  1565                              <1> ;;
  1566                              <1> ;; [swpq_last] = 0 to 4096 (step 4) -> the last position on the queue
  1567                              <1> ;;
  1568                              <1> ;; Method:
  1569                              <1> ;;	Swap page queue is a list of allocated pages with physical
  1570                              <1> ;;	addresses (system mode virtual adresses = physical addresses).
  1571                              <1> ;;	It is used for 'swap_in' and 'swap_out' procedures.
  1572                              <1> ;;	When a new page is being allocated, swap queue is updated
  1573                              <1> ;;	by 'swap_queue_shift' procedure, header of the queue (offset 0)
  1574                              <1> ;;	is checked for 'accessed' flag. If the 1st page on the queue
  1575                              <1> ;;	is 'accessed' or 'read only', it is dropped from the list;
  1576                              <1> ;;	other pages from the 2nd to the last (in [swpq_last]) shifted
  1577                              <1> ;; 	to head then the 2nd page becomes the 1st and '[swpq_last]' 
  1578                              <1> ;;	offset value becomes it's previous offset value - 4.
  1579                              <1> ;;	If the 1st page of the swap page queue is not 'accessed'	
  1580                              <1> ;;	the queue/list is not shifted.
  1581                              <1> ;;	After the queue/list shift, newly allocated page is added
  1582                              <1> ;;	to the tail of the queue at the [swpq_count*4] position.
  1583                              <1> ;;	But, if [swpq_count] > 1023, the newly allocated page
  1584                              <1> ;;	will not be added to the tail of swap page queue.  		 
  1585                              <1> ;;	
  1586                              <1> ;;	During 'swap_out' procedure, swap page queue is checked for
  1587                              <1> ;;	the first non-accessed, writable page in the list, 
  1588                              <1> ;;	from the head to the tail. The list is shifted to left 
  1589                              <1> ;;	(to the head) till a non-accessed page will be found in the list.
  1590                              <1> ;;	Then, this page	is swapped out (to disk) and then it is dropped
  1591                              <1> ;;	from the list by a final swap queue shift. [swpq_count] value
  1592                              <1> ;;	is changed. If all pages on the queue' are 'accessed', 
  1593                              <1> ;;	'insufficient memory' error will be returned ('swap_out' 
  1594                              <1> ;;	procedure will be failed)...
  1595                              <1> ;;
  1596                              <1> ;;	Note: If the 1st page of the queue is an 'accessed' page,
  1597                              <1> ;;	'accessed' flag of the page will be reset (0) and that page
  1598                              <1> ;;	(PTE) will be added to the tail of the queue after
  1599                              <1> ;;	the check, if [swpq_count] < 1023. If [swpq_count] = 1024
  1600                              <1> ;;	the queue will be rotated and the PTE in the head will be
  1601                              <1> ;;	added to the tail after resetting 'accessed' bit. 
  1602                              <1> ;;
  1603                              <1> ;;
  1604                              <1> ;;	
  1605                              <1> ;; SWAP DISK/FILE (with 4096 bytes swapped page blocks)
  1606                              <1> ;;
  1607                              <1> ;;  00000000  00000004  00000008  0000000C   ...   size-8    size-4
  1608                              <1> ;; +---------+---------+---------+---------+-- --+---------+---------+
  1609                              <1> ;; |descriptr| page(1) | page(2) | page(3) | ... |page(n-1)| page(n) |
  1610                              <1> ;; +---------+---------+---------+---------+-- --+---------+---------+    
  1611                              <1> ;;
  1612                              <1> ;; [swpd_next] = the first free block address in swapped page records
  1613                              <1> ;;    		 for next free block search by 'swap_out' procedure.
  1614                              <1> ;; [swpd_size] = swap disk/file size in sectors (512 bytes)
  1615                              <1> ;;		 NOTE: max. possible swap disk size is 1024 GB
  1616                              <1> ;; 		 (entire swap space must be accessed by using
  1617                              <1> ;;		 31 bit offset address) 
  1618                              <1> ;; [swpd_free] = free block (4096 bytes) count in swap disk/file space
  1619                              <1> ;; [swpd_start] = absolute/start address of the swap disk/file
  1620                              <1> ;;		  0 for file, or beginning sector of the swap partition
  1621                              <1> ;; [swp_drv] = logical drive description table addr. of swap disk/file
  1622                              <1> ;;
  1623                              <1> ;; 					
  1624                              <1> ;; Method:
  1625                              <1> ;;	When the memory (ram) becomes insufficient, page allocation
  1626                              <1> ;;	procedure swaps out a page from memory to the swap disk 
  1627                              <1> ;;	(partition) or swap file to get a new free page at the memory.
  1628                              <1> ;;	Swapping out is performed by using swap page queue.
  1629                              <1> ;;
  1630                              <1> ;; 	Allocation block size of swap disk/file is equal to page size
  1631                              <1> ;;	(4096 bytes). Swapping address (in sectors) is recorded
  1632                              <1> ;;	into relevant page file entry as 31 bit physical (logical)
  1633                              <1> ;;	offset address as 1 bit shifted to left for present flag (0).
  1634                              <1> ;;	Swapped page address is between 1 and swap disk/file size - 4.	  
  1635                              <1> ;;	Absolute physical (logical) address of the swapped page is 
  1636                              <1> ;;	calculated by adding offset value to the swap partition's 
  1637                              <1> ;;	start address. If the swap device (disk) is a virtual disk 
  1638                              <1> ;;	or it is a file, start address of the swap disk/volume is 0, 
  1639                              <1> ;;	and offset value is equal to absolute (physical or logical)
  1640                              <1> ;;	address/position. (It has not to be ZERO if the swap partition 
  1641                              <1> ;;	is in a partitioned virtual hard disk.) 
  1642                              <1> ;;
  1643                              <1> ;;	Note: Swap addresses are always specified/declared in sectors, 
  1644                              <1> ;;	not in bytes or	in blocks/zones/clusters (4096 bytes) as unit.
  1645                              <1> ;;
  1646                              <1> ;;	Swap disk/file allocation is mapped via 'Swap Allocation Table'
  1647                              <1> ;;	at memory as similar to 'Memory Allocation Table'.
  1648                              <1> ;;
  1649                              <1> ;;	Every bit of Swap Allocation Table repsesents one swap block
  1650                              <1> ;;	(equal to page size) respectively. Bit 0 of the S.A.T. byte 0
  1651                              <1> ;;	is reserved for swap disk/file block 0 as descriptor block
  1652                              <1> ;;	(also for compatibility with PTE). If bit value is ZERO,
  1653                              <1> ;;	it means relevant (respective) block is in use, and, 
  1654                              <1> ;;	of course, if bit value is 1, it means relevant (respective)
  1655                              <1> ;;      swap disk/file block is free.
  1656                              <1> ;;	For example: bit 1 of the byte 128 repsesents block 1025 
  1657                              <1> ;;	(128*8+1) or sector (offset) 8200 on the swap disk or
  1658                              <1> ;;	byte (offset/position) 4198400 in the swap file. 
  1659                              <1> ;;	4GB swap space is represented via 128KB Swap Allocation Table.
  1660                              <1> ;;	Initial layout of Swap Allocation Table is as follows:
  1661                              <1> ;;	------------------------------------------------------------
  1662                              <1> ;;	0111111111111111111111111 .... 11111111111111111111111111111
  1663                              <1> ;;	------------------------------------------------------------
  1664                              <1> ;;	(0 is reserved block, 1s represent free blocks respectively.)
  1665                              <1> ;;	(Note: Allocation cell/unit of the table is bit, not byte)
  1666                              <1> ;;
  1667                              <1> ;;	..............................................................
  1668                              <1> ;;
  1669                              <1> ;;	'swap_out' procedure checks 'free_swap_blocks' count at first,
  1670                              <1> ;;	then it searches Swap Allocation Table if free count is not
  1671                              <1> ;;	zero. From begining the [swpd_next] dword value, the first bit 
  1672                              <1> ;;	position with value of 1 on the table is converted to swap
  1673                              <1> ;;	disk/file offset address, in sectors (not 4096 bytes block).
  1674                              <1> ;;	'ldrv_write' procedure is called with ldrv (logical drive
  1675                              <1> ;;	number of physical swap disk or virtual swap disk)
  1676                              <1> ;;	number, sector offset (not absolute sector -LBA- number),
  1677                              <1> ;;	and sector count (8, 512*8 = 4096) and buffer adress
  1678                              <1> ;;	(memory page). That will be a direct disk write procedure.
  1679                              <1> ;;	(for preventing late memory allocation, significant waiting). 
  1680                              <1> ;;	If disk write procedure returns with error or free count of 
  1681                              <1> ;;	swap blocks is ZERO, 'swap_out' procedure will return with
  1682                              <1> ;;	'insufficient memory error' (cf=1). 
  1683                              <1> ;;
  1684                              <1> ;;	(Note: Even if free swap disk/file blocks was not zero,
  1685                              <1> ;;	any disk write error will not be fixed by 'swap_out' procedure,
  1686                              <1> ;;	in other words, 'swap_out' will not check the table for other
  1687                              <1> ;;	free blocks after a disk write error. It will return to 
  1688                              <1> ;;	the caller with error (CF=1) which means swapping is failed. 
  1689                              <1> ;;
  1690                              <1> ;;	After writing the page on to swap disk/file address/sector,
  1691                              <1> ;;	'swap_out' procesure returns with that swap (offset) sector
  1692                              <1> ;;	address (cf=0). 
  1693                              <1> ;;
  1694                              <1> ;;	..............................................................
  1695                              <1> ;;
  1696                              <1> ;;	'swap_in' procedure loads addressed (relevant) swap disk or
  1697                              <1> ;;	file sectors at specified memory page. Then page allocation
  1698                              <1> ;;	procedure updates relevant page table entry with 'present' 
  1699                              <1> ;;	attribute. If swap disk or file reading fails there is nothing
  1700                              <1> ;;	to do, except to terminate the process which is the owner of
  1701                              <1> ;;	the swapped page.
  1702                              <1> ;;
  1703                              <1> ;;	'swap_in' procedure sets the relevant/respective bit value
  1704                              <1> ;;	in the Swap Allocation Table (as free block). 'swap_in' also
  1705                              <1> ;;	updates [swpd_first] pointer if it is required.
  1706                              <1> ;;
  1707                              <1> ;;	..............................................................	 
  1708                              <1> ;;
  1709                              <1> ;;	Note: If [swap_enabled] value is ZERO, that means there is not
  1710                              <1> ;;	a swap disk or swap file in use... 'swap_in' and 'swap_out'
  1711                              <1> ;;	procedures ans 'swap page que' procedures will not be active...
  1712                              <1> ;;	'Insufficient memory' error will be returned by 'swap_out'
  1713                              <1> ;;	and 'general protection fault' will be returned by 'swap_in'
  1714                              <1> ;;	procedure, if it is called mistakenly (a wrong value in a PTE).		
  1715                              <1> ;;
  1716                              <1> 
  1717                              <1> swap_in:
  1718                              <1> 	; 31/08/2015
  1719                              <1> 	; 20/07/2015
  1720                              <1> 	; 28/04/2015
  1721                              <1> 	; 18/04/2015
  1722                              <1> 	; 24/10/2014 (Retro UNIX 386 v1 - beginning)
  1723                              <1> 	;
  1724                              <1> 	; INPUT -> 
  1725                              <1> 	;	EBX = PHYSICAL (real/flat) ADDRESS OF THE MEMORY PAGE
  1726                              <1> 	;	EBP = VIRTUAL (LINEAR) ADDRESS (page fault address)
  1727                              <1> 	;	EAX = Offset Address for the swapped page on the
  1728                              <1> 	;	      swap disk or in the swap file.
  1729                              <1> 	;
  1730                              <1> 	; OUTPUT ->
  1731                              <1> 	;	EAX = 0 if loading at memory has been successful
  1732                              <1> 	;
  1733                              <1> 	;	CF = 1 -> swap disk reading error (disk/file not present
  1734                              <1> 	;		  or sector not present or drive not ready
  1735                              <1> 	;	     EAX = Error code
  1736                              <1> 	;	     [u.error] = EAX 
  1737                              <1> 	;		       = The last error code for the process
  1738                              <1> 	;		         (will be reset after returning to user)	  
  1739                              <1> 	;
  1740                              <1> 	; Modified Registers -> EAX
  1741                              <1> 	;
  1742                              <1> 
  1743 00005724 833D[62050300]00    <1>         cmp     dword [swp_drv], 0
  1744 0000572B 7646                <1> 	jna	short swpin_dnp_err
  1745                              <1> 
  1746 0000572D 3B05[66050300]      <1> 	cmp	eax, [swpd_size]
  1747 00005733 734A                <1> 	jnb	short swpin_snp_err
  1748                              <1> 
  1749 00005735 56                  <1> 	push	esi
  1750 00005736 53                  <1> 	push	ebx
  1751 00005737 51                  <1> 	push	ecx
  1752 00005738 8B35[62050300]      <1> 	mov	esi, [swp_drv]	
  1753 0000573E B908000000          <1> 	mov	ecx, PAGE_SIZE / LOGIC_SECT_SIZE  ; 8 !
  1754                              <1> 		; Note: Even if corresponding physical disk's sector 
  1755                              <1> 		; size different than 512 bytes, logical disk sector
  1756                              <1> 		; size is 512 bytes and disk reading procedure
  1757                              <1> 		; will be performed for reading 4096 bytes
  1758                              <1> 		; (2*2048, 8*512). 
  1759                              <1> 	; ESI = Logical disk description table address
  1760                              <1> 	; EBX = Memory page (buffer) address (physical!)
  1761                              <1> 	; EAX = Sector adress (offset address, logical sector number)
  1762                              <1> 	; ECX = Sector count ; 8 sectors
  1763 00005743 50                  <1> 	push	eax
  1764 00005744 E8AF020000          <1> 	call	logical_disk_read
  1765 00005749 58                  <1> 	pop	eax
  1766 0000574A 730C                <1> 	jnc	short swpin_read_ok
  1767                              <1> 	;
  1768 0000574C B828000000          <1> 	mov	eax, SWP_DISK_READ_ERR ; drive not ready or read error
  1769 00005751 A3[C8030300]        <1> 	mov	[u.error], eax
  1770 00005756 EB17                <1> 	jmp	short swpin_retn
  1771                              <1> 	;
  1772                              <1> swpin_read_ok:
  1773                              <1> 	; EAX = Offset address (logical sector number)
  1774 00005758 E80D020000          <1> 	call	unlink_swap_block  ; Deallocate swap block	
  1775                              <1> 	;
  1776                              <1> 	; EBX = Memory page (buffer) address (physical!)
  1777                              <1> 	; 20/07/2015
  1778 0000575D 89EB                <1> 	mov	ebx, ebp ; virtual address (page fault address)
  1779 0000575F 6681E300F0          <1>         and     bx, ~PAGE_OFF ; ~0FFFh ; reset bits, 0 to 11
  1780 00005764 8A1D[B3030300]      <1> 	mov	bl, [u.uno] ; current process number
  1781                              <1> 	; EBX = Virtual (Linear) address & process number combination
  1782 0000576A E8DB000000          <1> 	call	swap_queue_shift
  1783                              <1> 	; eax = 0 ; 10/06/2016 (if ebx input > 0, eax output = 0)
  1784                              <1> 	;sub	eax, eax  ; 0 ; Error Code = 0  (no error)
  1785                              <1> 	; zf = 1
  1786                              <1> swpin_retn:
  1787 0000576F 59                  <1> 	pop	ecx
  1788 00005770 5B                  <1> 	pop	ebx
  1789 00005771 5E                  <1> 	pop	esi
  1790 00005772 C3                  <1> 	retn
  1791                              <1> 
  1792                              <1> swpin_dnp_err:
  1793 00005773 B829000000          <1> 	mov	eax, SWP_DISK_NOT_PRESENT_ERR
  1794                              <1> swpin_err_retn:
  1795 00005778 A3[C8030300]        <1> 	mov	[u.error], eax
  1796 0000577D F9                  <1> 	stc
  1797 0000577E C3                  <1> 	retn
  1798                              <1> 
  1799                              <1> swpin_snp_err:
  1800 0000577F B82A000000          <1> 	mov	eax, SWP_SECTOR_NOT_PRESENT_ERR
  1801 00005784 EBF2                <1> 	jmp	short swpin_err_retn
  1802                              <1> 
  1803                              <1> swap_out:
  1804                              <1> 	; 10/06/2016
  1805                              <1> 	; 07/06/2016
  1806                              <1>         ; 23/05/2016
  1807                              <1> 	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
  1808                              <1> 	; 24/10/2014 - 31/08/2015 (Retro UNIX 386 v1)
  1809                              <1> 	;
  1810                              <1> 	; INPUT -> 
  1811                              <1> 	;	none
  1812                              <1> 	;
  1813                              <1> 	; OUTPUT ->
  1814                              <1> 	;	EAX = Physical page address (which is swapped out
  1815                              <1> 	;	      for allocating a new page)
  1816                              <1> 	;	CF = 1 -> swap disk writing error (disk/file not present
  1817                              <1> 	;		  or sector not present or drive not ready
  1818                              <1> 	;	     EAX = Error code
  1819                              <1> 	;	     [u.error] = EAX 
  1820                              <1> 	;		       = The last error code for the process
  1821                              <1> 	;		         (will be reset after returning to user)	  
  1822                              <1> 	;
  1823                              <1> 	; Modified Registers -> none (except EAX)
  1824                              <1> 	;
  1825 00005786 66833D[60050300]01  <1> 	cmp 	word [swpq_count], 1
  1826 0000578E 0F82AF000000        <1>         jc      swpout_im_err ; 'insufficient memory'
  1827                              <1> 
  1828                              <1>         ;cmp    dword [swp_drv], 1
  1829                              <1> 	;jc	short swpout_dnp_err ; 'swap disk/file not present'
  1830                              <1> 
  1831 00005794 833D[6A050300]01    <1>         cmp     dword [swpd_free], 1
  1832 0000579B 0F828F000000        <1>         jc      swpout_nfspc_err ; 'no free space on swap disk'
  1833                              <1> 
  1834 000057A1 53                  <1> 	push	ebx ; *
  1835                              <1> swpout_1:
  1836                              <1> 	; 10/06/2016
  1837 000057A2 31DB                <1> 	xor	ebx, ebx ; shift the queue and return a PTE value
  1838 000057A4 E8A1000000          <1> 	call	swap_queue_shift
  1839 000057A9 21C0                <1> 	and	eax, eax	; 0 = empty queue (improper entries)
  1840 000057AB 0F848A000000        <1>         jz      swpout_npts_err        ; There is not any proper PTE
  1841                              <1> 				       ; pointer in the swap queue
  1842                              <1> 	; EAX = PTE value of the page
  1843                              <1> 	; EBX = PTE address of the page
  1844 000057B1 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear attribute bits
  1845                              <1> 	;
  1846                              <1> 	; 07/06/2016
  1847                              <1> 	; 19/05/2016
  1848                              <1> 	; check this page is in timer events or not
  1849                              <1> 	
  1850                              <1> swpout_timer_page_0:
  1851 000057B5 52                  <1> 	push	edx ; **
  1852                              <1> 
  1853                              <1> 	; 07/06/2016
  1854 000057B6 803D[136B0100]00    <1> 	cmp	byte [timer_events], 0 
  1855 000057BD 762F                <1> 	jna	short swpout_2
  1856                              <1> 	;
  1857 000057BF 8A15[136B0100]      <1> 	mov	dl, [timer_events]
  1858                              <1> 
  1859 000057C5 51                  <1> 	push	ecx ; ***
  1860 000057C6 53                  <1> 	push	ebx ; ****
  1861 000057C7 BB[60040300]        <1> 	mov	ebx, timer_set ; beginning address of timer event
  1862                              <1> 			       ; structures 
  1863                              <1> swpout_timer_page_1:
  1864 000057CC 8A0B                <1> 	mov	cl, [ebx]
  1865 000057CE 08C9                <1> 	or	cl, cl ; 0 = free, >0 = process number
  1866 000057D0 7415                <1> 	jz	short swpout_timer_page_3
  1867 000057D2 8B4B0C              <1> 	mov	ecx, [ebx+12] ; response (signal return) address
  1868 000057D5 6681E100F0          <1> 	and	cx, PTE_A_CLEAR ; clear offset part (right 12 bits)
  1869                              <1> 				; of the response byte address, to
  1870                              <1> 				; get beginning of the page address)
  1871 000057DA 39C8                <1> 	cmp	eax, ecx
  1872 000057DC 7505                <1> 	jne	short swpout_timer_page_2 ; not same page
  1873                              <1> 	
  1874                              <1> 	; !same page!
  1875                              <1> 	;
  1876                              <1> 	; NOTE: // 19/05/2016 // - TRDOS 386 feature only ! -
  1877                              <1> 	; This page will be used by the kernel to put timer event
  1878                              <1> 	; response (signal return) byte at the requested address;
  1879                              <1> 	; in order to prevent a possible wrong write (while
  1880                              <1> 	; this page is swapped out) on physical memory,
  1881                              <1> 	; we must protect this page against to be swapped out!
  1882                              <1> 	;
  1883 000057DE 5B                  <1> 	pop	ebx ; ****
  1884 000057DF 59                  <1> 	pop	ecx ; ***
  1885 000057E0 5A                  <1> 	pop	edx ; **
  1886 000057E1 EBBF                <1> 	jmp	short swpout_1	; do not swap out this page !
  1887                              <1>  
  1888                              <1> swpout_timer_page_2:
  1889                              <1> 	; 07/06/2016
  1890 000057E3 FECA                <1> 	dec	dl
  1891 000057E5 7405                <1> 	jz	short swpout_timer_page_4
  1892                              <1> swpout_timer_page_3:
  1893                              <1> 	;cmp	ebx, timer_set + 240 ; last timer event (15*16) 
  1894                              <1> 	;jnb	short swpout_timer_page_4
  1895 000057E7 83C310              <1> 	add	ebx, 16
  1896 000057EA EBE0                <1> 	jmp	short swpout_timer_page_1	
  1897                              <1> 
  1898                              <1> swpout_timer_page_4:
  1899 000057EC 5B                  <1> 	pop	ebx ; ****
  1900 000057ED 59                  <1> 	pop	ecx ; ***
  1901                              <1> swpout_2:
  1902 000057EE 89DA                <1> 	mov	edx, ebx	       ; Page table entry address	
  1903 000057F0 89C3                <1> 	mov	ebx, eax	       ; Buffer (Page) Address				
  1904                              <1> 	;
  1905 000057F2 E8A6010000          <1> 	call	link_swap_block
  1906 000057F7 7304                <1> 	jnc	short swpout_3	       ; It may not be needed here	
  1907                              <1> 				       ; because [swpd_free] value
  1908                              <1> 				       ; was checked at the beginging. 	
  1909 000057F9 5A                  <1> 	pop	edx ; **
  1910 000057FA 5B                  <1> 	pop	ebx ; *
  1911 000057FB EB33                <1> 	jmp	short swpout_nfspc_err 
  1912                              <1> swpout_3:
  1913 000057FD A900000080          <1> 	test	eax, 80000000h ; test bit 31 (this may not be needed!)
  1914 00005802 752C                <1> 	jnz	short swpout_nfspc_err  ; 10/06/2016 (bit 31 = 1 !)
  1915                              <1> 	;	
  1916 00005804 56                  <1> 	push	esi ; **
  1917 00005805 51                  <1> 	push	ecx ; ***
  1918 00005806 50                  <1> 	push	eax ; sector address ; (31 bit !, bit 31 = 0)
  1919 00005807 8B35[62050300]      <1> 	mov	esi, [swp_drv]	
  1920 0000580D B908000000          <1> 	mov	ecx, PAGE_SIZE / LOGIC_SECT_SIZE  ; 8 !
  1921                              <1> 		; Note: Even if corresponding physical disk's sector 
  1922                              <1> 		; size different than 512 bytes, logical disk sector
  1923                              <1> 		; size is 512 bytes and disk writing procedure
  1924                              <1> 		; will be performed for writing 4096 bytes
  1925                              <1> 		; (2*2048, 8*512). 
  1926                              <1> 	; ESI = Logical disk description table address
  1927                              <1> 	; EBX = Buffer (Page) address
  1928                              <1> 	; EAX = Sector adress (offset address, logical sector number)
  1929                              <1> 	; ECX = Sector count ; 8 sectors
  1930                              <1> 	; edx = PTE address
  1931 00005812 E8E2010000          <1> 	call	logical_disk_write
  1932                              <1> 	; edx = PTE address
  1933 00005817 59                  <1> 	pop	ecx ; sector address	
  1934 00005818 730C                <1> 	jnc	short swpout_write_ok
  1935                              <1> 	;
  1936                              <1> 	;; call	unlink_swap_block ; this block must be left as 'in use'
  1937                              <1> swpout_dw_err:
  1938 0000581A B82C000000          <1> 	mov	eax, SWP_DISK_WRITE_ERR ; drive not ready or write error
  1939 0000581F A3[C8030300]        <1> 	mov	[u.error], eax
  1940 00005824 EB06                <1> 	jmp	short swpout_retn
  1941                              <1> 	;
  1942                              <1> swpout_write_ok:
  1943                              <1> 	; EBX = Buffer (page) address
  1944                              <1> 	; EDX = Page Table Entry address
  1945                              <1> 	; ECX = Swap disk sector (file block) address (31 bit)
  1946 00005826 D1E1                <1> 	shl 	ecx, 1  ; 31 bit sector address from bit 1 to bit 31 
  1947 00005828 890A                <1> 	mov 	[edx], ecx 
  1948                              <1> 		; bit 0 = 0 (swapped page)
  1949 0000582A 89D8                <1> 	mov	eax, ebx
  1950                              <1> swpout_retn:
  1951 0000582C 59                  <1> 	pop	ecx ; ***
  1952 0000582D 5E                  <1> 	pop	esi ; **
  1953 0000582E 5B                  <1> 	pop	ebx ; *
  1954 0000582F C3                  <1> 	retn
  1955                              <1> 
  1956                              <1> ;swpout_dnp_err:
  1957                              <1> ;	mov	eax, SWP_DISK_NOT_PRESENT_ERR ; disk not present
  1958                              <1> ;	jmp	short swpout_err_retn
  1959                              <1> swpout_nfspc_err:
  1960 00005830 B82B000000          <1> 	mov	eax, SWP_NO_FREE_SPACE_ERR ; no free space
  1961                              <1> swpout_err_retn:
  1962 00005835 A3[C8030300]        <1> 	mov	[u.error], eax
  1963                              <1> 	;stc
  1964 0000583A C3                  <1> 	retn
  1965                              <1> swpout_npts_err:
  1966 0000583B B82D000000          <1> 	mov	eax, SWP_NO_PAGE_TO_SWAP_ERR
  1967 00005840 5B                  <1> 	pop	ebx
  1968 00005841 EBF2                <1> 	jmp	short swpout_err_retn
  1969                              <1> swpout_im_err:
  1970 00005843 B804000000          <1> 	mov	eax, ERR_MINOR_IM ; insufficient (out of) memory
  1971 00005848 EBEB                <1> 	jmp	short swpout_err_retn
  1972                              <1> 
  1973                              <1> swap_queue_shift:
  1974                              <1> 	; 26/03/2017
  1975                              <1> 	; 10/06/2016
  1976                              <1> 	; 09/06/2016 - TRDOS 386 (TRDOS v2.0)
  1977                              <1> 	; 23/10/2014 - 20/07/2015 (Retro UNIX 386 v1)
  1978                              <1> 	;
  1979                              <1> 	; INPUT ->
  1980                              <1> 	;	EBX = Virtual (linear) address (bit 12 to 31) 
  1981                              <1> 	;	      and process number combination (bit 0 to 11)
  1982                              <1> 	;	EBX = 0 -> shift/drop from the head (offset 0)
  1983                              <1> 	;	
  1984                              <1> 	; OUTPUT ->
  1985                              <1> 	;	If EBX input > 0 
  1986                              <1> 	;	   the queue will be shifted 4 bytes (dword),
  1987                              <1> 	; 	   from the tail to the head, up to entry offset
  1988                              <1> 	; 	   which points to EBX input value or nothing
  1989                              <1> 	;	   to do if EBX value is not found on the queue.
  1990                              <1> 	;	   (The entry -with EBX value- will be removed
  1991                              <1> 	;	   from the queue if it is found.)
  1992                              <1> 	;
  1993                              <1> 	;	   EAX = 0		
  1994                              <1> 	;
  1995                              <1> 	;	If EBX input = 0
  1996                              <1> 	;	   the queue will be shifted 4 bytes (dword),
  1997                              <1> 	; 	   from the tail to the head, if the PTE address
  1998                              <1> 	;	   which is pointed in head of the queue is marked
  1999                              <1> 	;	   as "accessed" or it is marked as "non present".
  2000                              <1> 	;	   (If "accessed" flag of the PTE -which is pointed
  2001                              <1> 	;	   in the head- is set -to 1-, it will be reset
  2002                              <1> 	;	   -to 0- and then, the queue will be rotated 
  2003                              <1> 	;	   -without dropping pointer of the PTE from 
  2004                              <1> 	;	   the queue- for 4 bytes on head to tail direction.
  2005                              <1> 	;	   Pointer in the head will be moved into the tail,
  2006                              <1> 	;	   other PTEs will be shifted on head direction.)
  2007                              <1> 	;
  2008                              <1> 	;	   Swap queue will be shifted up to the first
  2009                              <1> 	;	   'present' or 'non accessed' page will be found
  2010                              <1> 	;	   (as pointed) on the queue head (then it will be
  2011                              <1>         ;          removed/dropped from the queue).
  2012                              <1> 	;
  2013                              <1> 	;	   EAX (> 0) = PTE value of the page which is
  2014                              <1> 	;		 (it's pointer -virtual address-) dropped
  2015                              <1> 	;		 (removed) from swap queue.
  2016                              <1> 	;	   EBX = PTE address of the page (if EAX > 0)
  2017                              <1> 	;	         which is (it's pointer -virtual address-)
  2018                              <1> 	;		 dropped (removed) from swap queue.
  2019                              <1> 	;
  2020                              <1> 	;	   EAX = 0 -> empty swap queue ! 
  2021                              <1> 	;
  2022                              <1> 	; Modified Registers -> EAX, EBX
  2023                              <1> 	;
  2024 0000584A 0FB705[60050300]    <1> 	movzx   eax, word [swpq_count]  ; Max. 1024
  2025 00005851 6621C0              <1> 	and	ax, ax
  2026 00005854 7431                <1> 	jz	short swpqs_retn
  2027 00005856 57                  <1> 	push	edi
  2028 00005857 56                  <1> 	push	esi
  2029 00005858 51                  <1> 	push	ecx
  2030 00005859 BE00E00800          <1> 	mov	esi, swap_queue
  2031 0000585E 89C1                <1> 	mov	ecx, eax
  2032 00005860 09DB                <1> 	or	ebx, ebx
  2033 00005862 7424                <1> 	jz	short swpqs_7
  2034                              <1> swpqs_1:
  2035 00005864 AD                  <1> 	lodsd
  2036 00005865 39D8                <1> 	cmp	eax, ebx
  2037 00005867 7406                <1> 	je	short swpqs_2
  2038 00005869 E2F9                <1> 	loop	swpqs_1
  2039                              <1> 	; 10/06/2016
  2040 0000586B 29C0                <1> 	sub	eax, eax 
  2041 0000586D EB15                <1> 	jmp	short swpqs_6
  2042                              <1> swpqs_2:
  2043 0000586F 89F7                <1> 	mov	edi, esi
  2044 00005871 83EF04              <1> 	sub 	edi, 4
  2045                              <1> swpqs_3:
  2046 00005874 66FF0D[60050300]    <1> 	dec	word [swpq_count]
  2047 0000587B 7403                <1> 	jz	short swpqs_5
  2048                              <1> swpqs_4:
  2049 0000587D 49                  <1> 	dec 	ecx
  2050 0000587E F3A5                <1> 	rep	movsd	; shift up (to the head)
  2051                              <1> swpqs_5:
  2052 00005880 31C0                <1> 	xor	eax, eax
  2053 00005882 8907                <1> 	mov	[edi], eax
  2054                              <1> swpqs_6:
  2055 00005884 59                  <1> 	pop	ecx
  2056 00005885 5E                  <1> 	pop	esi
  2057 00005886 5F                  <1> 	pop	edi
  2058                              <1> swpqs_retn:
  2059 00005887 C3                  <1> 	retn		
  2060                              <1> swpqs_7:
  2061 00005888 89F7                <1> 	mov	edi, esi ; head
  2062 0000588A AD                  <1> 	lodsd
  2063                              <1> 	; 20/07/2015
  2064 0000588B 89C3                <1> 	mov	ebx, eax
  2065 0000588D 81E300F0FFFF        <1> 	and	ebx, ~PAGE_OFF ; ~0FFFh 
  2066                              <1> 		      ; ebx = virtual address (at page boundary)	
  2067 00005893 25FF0F0000          <1> 	and	eax, PAGE_OFF ; 0FFFh
  2068                              <1> 		      ; ax = process number (1 to 4095)
  2069 00005898 3A05[B3030300]      <1> 	cmp	al, [u.uno]
  2070                              <1> 		; Max. 16 (nproc) processes for Retro UNIX 386 v1
  2071 0000589E 7507                <1> 	jne	short swpqs_8
  2072 000058A0 A1[B8030300]        <1> 	mov	eax, [u.pgdir]
  2073 000058A5 EB28                <1> 	jmp	short swpqs_9
  2074                              <1> swpqs_8:
  2075                              <1> 	; 09/06/2016
  2076 000058A7 80B8[AF000300]00    <1> 	cmp	byte [eax+p.stat-1], 0
  2077 000058AE 76C4                <1> 	jna	short swpqs_3     ; free (or terminated) process
  2078 000058B0 80B8[AF000300]02    <1> 	cmp	byte [eax+p.stat-1], 2 ; waiting
  2079 000058B7 77BB                <1> 	ja	short swpqs_3 	  ; zombie (3) or undefined ?	
  2080                              <1> 
  2081                              <1> 	;shl	ax, 2
  2082 000058B9 C0E002              <1> 	shl	al, 2
  2083 000058BC 8B80[BC000300]      <1> 	mov 	eax, [eax+p.upage-4]
  2084 000058C2 09C0                <1> 	or	eax, eax
  2085 000058C4 74AE                <1> 	jz	short swpqs_3 ; invalid upage
  2086 000058C6 83C05C              <1> 	add	eax, u.pgdir - user
  2087                              <1> 			 ; u.pgdir value for the process
  2088                              <1> 			 ; is in [eax]
  2089 000058C9 8B00                <1> 	mov	eax, [eax]
  2090 000058CB 21C0                <1> 	and	eax, eax
  2091 000058CD 74A5                <1> 	jz	short swpqs_3 ; invalid page directory
  2092                              <1> swpqs_9:
  2093 000058CF 52                  <1> 	push	edx
  2094                              <1> 	; eax = page directory
  2095                              <1> 	; ebx = virtual address
  2096 000058D0 E82BFBFFFF          <1> 	call	get_pte
  2097 000058D5 89D3                <1> 	mov	ebx, edx	; PTE address
  2098 000058D7 5A                  <1> 	pop	edx
  2099                              <1> 	; 10/06/2016
  2100 000058D8 723A                <1> 	jc	short swpqs_13 ; empty PDE
  2101                              <1> 	; EAX = PTE value
  2102 000058DA A801                <1> 	test	al, PTE_A_PRESENT ; bit 0 = 1
  2103 000058DC 7436                <1> 	jz	short swpqs_13  ; Drop non-present page
  2104                              <1> 			        ; from the queue (head)
  2105 000058DE A802                <1> 	test	al, PTE_A_WRITE	; bit 1 = 0 (read only)
  2106 000058E0 7432                <1> 	jz	short swpqs_13  ; Drop read only page
  2107                              <1> 			        ; from the queue (head) 	
  2108                              <1> 	;test	al, PTE_A_ACCESS ; bit 5 = 1 (Accessed)
  2109                              <1> 	;jnz	short swpqs_11  ; present
  2110                              <1> 			        ; accessed page
  2111 000058E2 0FBAF005            <1>         btr     eax, PTE_A_ACCESS_BIT ; reset 'accessed' bit
  2112 000058E6 7210                <1> 	jc	short swpqs_11  ; accessed page
  2113                              <1> 
  2114 000058E8 49                  <1> 	dec	ecx
  2115 000058E9 66890D[60050300]    <1> 	mov	[swpq_count], cx
  2116 000058F0 7402                <1>         jz      short swpqs_10
  2117                              <1> 		; esi = head + 4
  2118                              <1> 		; edi = head
  2119 000058F2 F3A5                <1> 	rep	movsd	 ; n = 1 to k-1, [n - 1] = [n]
  2120                              <1> swpqs_10:
  2121 000058F4 890F                <1> 	mov	[edi], ecx ; 0
  2122 000058F6 EB8C                <1> 	jmp	short swpqs_6 ; 26/03/2017
  2123                              <1> 
  2124                              <1> swpqs_11:
  2125 000058F8 8903                <1> 	mov	[ebx], eax     ; save changed attribute
  2126                              <1> 	; Rotation (head -> tail)
  2127 000058FA 49                  <1> 	dec	ecx     ; entry count -> last entry number		
  2128 000058FB 74F7                <1> 	jz	short swpqs_10
  2129                              <1> 		; esi = head + 4
  2130                              <1> 		; edi = head
  2131 000058FD 8B07                <1> 	mov	eax, [edi] ; 20/07/2015
  2132 000058FF F3A5                <1> 	rep	movsd	 ; n = 1 to k-1, [n - 1] = [n]
  2133 00005901 8907                <1> 	mov	[edi], eax ; head -> tail ; [k] = [1]
  2134                              <1> 
  2135 00005903 668B0D[60050300]    <1> 	mov	cx, [swpq_count]
  2136                              <1> 
  2137                              <1> swpqs_12:
  2138 0000590A BE00E00800          <1> 	mov	esi, swap_queue ; head
  2139 0000590F E974FFFFFF          <1>         jmp     swpqs_7
  2140                              <1> 
  2141                              <1> swpqs_13:
  2142 00005914 49                  <1> 	dec	ecx
  2143 00005915 66890D[60050300]    <1> 	mov	[swpq_count], cx
  2144 0000591C 0F845EFFFFFF        <1>         jz      swpqs_5
  2145 00005922 EBE6                <1> 	jmp	short swpqs_12
  2146                              <1> 
  2147                              <1> add_to_swap_queue:
  2148                              <1> ; temporary - 16/09/2015
  2149 00005924 C3                  <1> retn
  2150                              <1> 	; 20/02/2017
  2151                              <1> 	; 20/07/2015
  2152                              <1> 	; 24/10/2014 (Retro UNIX 386 v1 - beginning)
  2153                              <1> 	;
  2154                              <1> 	; Adds new page to swap queue
  2155                              <1> 	; (page directories and page tables must not be added
  2156                              <1> 	; to swap queue)	
  2157                              <1> 	;
  2158                              <1> 	; INPUT ->
  2159                              <1> 	;	EBX = Linear (Virtual) addr for current process
  2160                              <1> 	;	[u.uno]
  2161                              <1> 	;	20/02/2017
  2162                              <1> 	;	(Linear address = CORE + user's virtual address)
  2163                              <1> 	;
  2164                              <1> 	; OUTPUT ->
  2165                              <1> 	;	EAX = [swpq_count]
  2166                              <1> 	;	      (after the PTE has been added)
  2167                              <1> 	;	EAX = 0 -> Swap queue is full, (1024 entries)
  2168                              <1> 	;	      the PTE could not be added.
  2169                              <1> 	;
  2170                              <1> 	; Modified Registers -> EAX
  2171                              <1> 	;
  2172 00005925 53                  <1> 	push	ebx
  2173 00005926 6681E300F0          <1>         and     bx, ~PAGE_OFF ; ~0FFFh ; reset bits, 0 to 11
  2174 0000592B 8A1D[B3030300]      <1> 	mov	bl, [u.uno] ; current process number
  2175 00005931 E814FFFFFF          <1> 	call	swap_queue_shift ; drop from the queue if
  2176                              <1> 				 ; it is already on the queue
  2177                              <1> 		; then add it to the tail of the queue
  2178 00005936 0FB705[60050300]    <1> 	movzx	eax, word [swpq_count]
  2179 0000593D 663D0004            <1> 	cmp	ax, 1024
  2180 00005941 7205                <1> 	jb	short atsq_1
  2181 00005943 6629C0              <1> 	sub	ax, ax
  2182 00005946 5B                  <1> 	pop	ebx
  2183 00005947 C3                  <1> 	retn
  2184                              <1> atsq_1:
  2185 00005948 56                  <1> 	push	esi
  2186 00005949 BE00E00800          <1> 	mov	esi, swap_queue
  2187 0000594E 6621C0              <1> 	and	ax, ax
  2188 00005951 740A                <1> 	jz	short atsq_2
  2189 00005953 66C1E002            <1> 	shl	ax, 2	; convert to offset
  2190 00005957 01C6                <1> 	add	esi, eax
  2191 00005959 66C1E802            <1> 	shr	ax, 2
  2192                              <1> atsq_2:
  2193 0000595D 6640                <1> 	inc	ax
  2194 0000595F 891E                <1> 	mov	[esi], ebx ; Virtual address + [u.uno] combination
  2195 00005961 66A3[60050300]      <1> 	mov	[swpq_count], ax
  2196 00005967 5E                  <1> 	pop	esi
  2197 00005968 5B                  <1> 	pop	ebx
  2198 00005969 C3                  <1> 	retn
  2199                              <1> 
  2200                              <1> unlink_swap_block:
  2201                              <1> 	; 15/09/2015
  2202                              <1> 	; 30/04/2015
  2203                              <1> 	; 18/04/2015
  2204                              <1> 	; 24/10/2014 (Retro UNIX 386 v1 - beginning)
  2205                              <1> 	;
  2206                              <1> 	; INPUT -> 
  2207                              <1> 	;	EAX = swap disk/file offset address
  2208                              <1> 	;	      (bit 1 to bit 31)
  2209                              <1> 	; OUTPUT ->
  2210                              <1> 	;	[swpd_free] is increased
  2211                              <1> 	;	(corresponding SWAP DISK ALLOC. TABLE bit is SET)
  2212                              <1> 	;
  2213                              <1> 	; Modified Registers -> EAX
  2214                              <1> 	;
  2215 0000596A 53                  <1> 	push	ebx
  2216 0000596B 52                  <1> 	push	edx
  2217                              <1> 	;
  2218 0000596C C1E804              <1> 	shr	eax, SECTOR_SHIFT+1  ;3+1 ; shift sector address to 
  2219                              <1> 				     ; 3 bits right
  2220                              <1> 				     ; to get swap block/page number
  2221 0000596F 89C2                <1> 	mov	edx, eax
  2222                              <1> 	; 15/09/2015
  2223 00005971 C1EA03              <1> 	shr	edx, 3		     ; to get offset to S.A.T.
  2224                              <1> 				     ; (1 allocation bit = 1 page)
  2225                              <1> 				     ; (1 allocation bytes = 8 pages)
  2226 00005974 80E2FC              <1> 	and	dl, 0FCh 	     ; clear lower 2 bits
  2227                              <1> 				     ; (to get 32 bit position)			
  2228                              <1> 	;
  2229 00005977 BB00000D00          <1> 	mov	ebx, swap_alloc_table ; Swap Allocation Table address
  2230 0000597C 01D3                <1> 	add	ebx, edx
  2231 0000597E 83E01F              <1> 	and	eax, 1Fh	     ; lower 5 bits only
  2232                              <1> 				     ; (allocation bit position)	 
  2233 00005981 3B05[6E050300]      <1> 	cmp 	eax, [swpd_next]     ; is the new free block addr. lower
  2234                              <1> 				     ; than the address in 'swpd_next' ?
  2235                              <1> 				     ; (next/first free block value)		
  2236 00005987 7305                <1> 	jnb	short uswpbl_1	     ; no	
  2237 00005989 A3[6E050300]        <1> 	mov	[swpd_next], eax     ; yes	
  2238                              <1> uswpbl_1:
  2239 0000598E 0FAB03              <1> 	bts	[ebx], eax	     ; unlink/release/deallocate block
  2240                              <1> 				     ; set relevant bit to 1.
  2241                              <1> 				     ; set CF to the previous bit value	
  2242 00005991 F5                  <1> 	cmc			     ; complement carry flag	
  2243 00005992 7206                <1> 	jc	short uswpbl_2	     ; do not increase swfd_free count
  2244                              <1> 				     ; if the block is already deallocated
  2245                              <1> 				     ; before.	
  2246 00005994 FF05[6A050300]      <1>         inc     dword [swpd_free]
  2247                              <1> uswpbl_2:
  2248 0000599A 5A                  <1> 	pop	edx
  2249 0000599B 5B                  <1> 	pop	ebx
  2250 0000599C C3                  <1> 	retn
  2251                              <1> 
  2252                              <1> link_swap_block:
  2253                              <1> 	; 01/07/2015
  2254                              <1> 	; 18/04/2015
  2255                              <1> 	; 24/10/2014 (Retro UNIX 386 v1 - beginning)
  2256                              <1> 	;
  2257                              <1> 	; INPUT -> none
  2258                              <1> 	;
  2259                              <1> 	; OUTPUT ->
  2260                              <1> 	;	EAX = OFFSET ADDRESS OF THE ALLOCATED BLOCK (4096 bytes)
  2261                              <1> 	;	      in sectors (corresponding 
  2262                              <1> 	;	      SWAP DISK ALLOCATION TABLE bit is RESET)
  2263                              <1> 	;
  2264                              <1> 	;	CF = 1 and EAX = 0 
  2265                              <1> 	; 		   if there is not a free block to be allocated	
  2266                              <1> 	;
  2267                              <1> 	; Modified Registers -> none (except EAX)
  2268                              <1> 	;
  2269                              <1> 
  2270                              <1> 	;mov	eax, [swpd_free]
  2271                              <1> 	;and	eax, eax
  2272                              <1> 	;jz	short out_of_swpspc
  2273                              <1> 	;
  2274 0000599D 53                  <1> 	push	ebx
  2275 0000599E 51                  <1> 	push	ecx
  2276                              <1> 	;
  2277 0000599F BB00000D00          <1> 	mov	ebx, swap_alloc_table ; Swap Allocation Table offset
  2278 000059A4 89D9                <1> 	mov	ecx, ebx
  2279 000059A6 031D[6E050300]      <1> 	add	ebx, [swpd_next] ; Free block searching starts from here
  2280                              <1> 				 ; next_free_swap_block >> 5
  2281 000059AC 030D[72050300]      <1> 	add	ecx, [swpd_last] ; Free block searching ends here
  2282                              <1> 				 ; (total_swap_blocks - 1) >> 5
  2283                              <1> lswbl_scan:
  2284 000059B2 39CB                <1> 	cmp	ebx, ecx
  2285 000059B4 770A                <1> 	ja	short lswbl_notfound
  2286                              <1> 	;
  2287 000059B6 0FBC03              <1> 	bsf	eax, [ebx] ; Scans source operand for first bit set (1).
  2288                              <1> 			   ; Clears ZF if a bit is found set (1) and 
  2289                              <1> 			   ; loads the destination with an index to
  2290                              <1> 			   ; first set bit. (0 -> 31) 
  2291                              <1> 			   ; Sets ZF to 1 if no bits are found set.
  2292                              <1> 	; 01/07/2015
  2293 000059B9 751C                <1> 	jnz	short lswbl_found ; ZF = 0 -> a free block has been found
  2294                              <1> 			 ;
  2295                              <1> 			 ; NOTE:  a Swap Disk Allocation Table bit 
  2296                              <1> 			 ;	  with value of 1 means 
  2297                              <1> 			 ;	  the corresponding page is free 
  2298                              <1> 			 ;	  (Retro UNIX 386 v1 feaure only!)
  2299 000059BB 83C304              <1> 	add	ebx, 4
  2300                              <1> 			 ; We return back for searching next page block
  2301                              <1> 			 ; NOTE: [swpd_free] is not ZERO; so, 
  2302                              <1> 			 ;	 we always will find at least 1 free block here.
  2303 000059BE EBF2                <1> 	jmp    	short lswbl_scan
  2304                              <1> 	;
  2305                              <1> lswbl_notfound:	
  2306 000059C0 81E900000D00        <1> 	sub	ecx, swap_alloc_table
  2307 000059C6 890D[6E050300]      <1> 	mov	[swpd_next], ecx ; next/first free page = last page 
  2308                              <1> 				 ; (unlink_swap_block procedure will change it)
  2309 000059CC 31C0                <1> 	xor	eax, eax
  2310 000059CE A3[6A050300]        <1> 	mov	[swpd_free], eax
  2311 000059D3 F9                  <1> 	stc
  2312                              <1> lswbl_ok:
  2313 000059D4 59                  <1> 	pop	ecx
  2314 000059D5 5B                  <1> 	pop	ebx
  2315 000059D6 C3                  <1> 	retn
  2316                              <1> 	;
  2317                              <1> ;out_of_swpspc:
  2318                              <1> ;	stc
  2319                              <1> ;	retn
  2320                              <1> 
  2321                              <1> lswbl_found:
  2322 000059D7 89D9                <1> 	mov	ecx, ebx
  2323 000059D9 81E900000D00        <1> 	sub	ecx, swap_alloc_table
  2324 000059DF 890D[6E050300]      <1> 	mov	[swpd_next], ecx ; Set first free block searching start
  2325                              <1> 				 ; address/offset (to the next)
  2326 000059E5 FF0D[6A050300]      <1>         dec     dword [swpd_free] ; 1 block has been allocated (X = X-1) 
  2327                              <1> 	;
  2328 000059EB 0FB303              <1> 	btr	[ebx], eax	 ; The destination bit indexed by the source value
  2329                              <1> 				 ; is copied into the Carry Flag and then cleared
  2330                              <1> 				 ; in the destination.
  2331                              <1> 				 ;
  2332                              <1> 				 ; Reset the bit which is corresponding to the 
  2333                              <1> 				 ; (just) allocated block.
  2334 000059EE C1E105              <1> 	shl	ecx, 5		 ; (block offset * 32) + block index
  2335 000059F1 01C8                <1> 	add	eax, ecx	 ; = block number
  2336 000059F3 C1E003              <1> 	shl	eax, SECTOR_SHIFT ; 3, sector (offset) address of the block
  2337                              <1> 				 ; 1 block =  8 sectors
  2338                              <1> 	;
  2339                              <1> 	; EAX = offset address of swap disk/file sector (beginning of the block)
  2340                              <1> 	;
  2341                              <1> 	; NOTE: The relevant page table entry will be updated
  2342                              <1> 	;       according to this EAX value...
  2343                              <1> 	;
  2344 000059F6 EBDC                <1> 	jmp	short lswbl_ok
  2345                              <1> 
  2346                              <1> logical_disk_read:
  2347                              <1> 	; 20/07/2015
  2348                              <1> 	; 09/03/2015 (temporary code here)
  2349                              <1> 	;
  2350                              <1> 	; INPUT ->
  2351                              <1> 	; 	ESI = Logical disk description table address
  2352                              <1> 	; 	EBX = Memory page (buffer) address (physical!)
  2353                              <1> 	; 	EAX = Sector adress (offset address, logical sector number)
  2354                              <1> 	; 	ECX = Sector count
  2355                              <1> 	;
  2356                              <1> 	;
  2357 000059F8 C3                  <1> 	retn
  2358                              <1> 
  2359                              <1> logical_disk_write:
  2360                              <1> 	; 20/07/2015
  2361                              <1> 	; 09/03/2015 (temporary code here)
  2362                              <1> 	;
  2363                              <1> 	; INPUT ->
  2364                              <1> 	; 	ESI = Logical disk description table address
  2365                              <1> 	; 	EBX = Memory page (buffer) address (physical!)
  2366                              <1> 	; 	EAX = Sector adress (offset address, logical sector number)
  2367                              <1> 	; 	ECX = Sector count
  2368                              <1> 	;
  2369 000059F9 C3                  <1> 	retn
  2370                              <1> 
  2371                              <1> get_physical_addr:
  2372                              <1> 	; 26/03/2017
  2373                              <1> 	; 20/02/2017
  2374                              <1> 	; 27/05/2016 - TRDOS 386 (TRDOS v2.0)
  2375                              <1> 	; 18/10/2015
  2376                              <1> 	; 29/07/2015
  2377                              <1> 	; 20/07/2015
  2378                              <1> 	; 04/06/2015
  2379                              <1> 	; 20/05/2015
  2380                              <1> 	; 28/04/2015
  2381                              <1> 	; 18/04/2015
  2382                              <1> 	; Get physical address
  2383                              <1> 	;     (allocates a new page for user if it is not present)
  2384                              <1> 	;	
  2385                              <1> 	; (This subroutine is needed for mapping user's virtual 
  2386                              <1> 	; (buffer) address to physical address (of the buffer).)
  2387                              <1> 	; ('sys write', 'sys read' system calls...)
  2388                              <1> 	;
  2389                              <1> 	; INPUT ->
  2390                              <1> 	;	EBX = virtual address
  2391                              <1> 	;	u.pgdir = page directory (physical) address
  2392                              <1> 	;
  2393                              <1> 	; OUTPUT ->
  2394                              <1> 	;	EAX = physical address 
  2395                              <1> 	;	EBX = linear address	
  2396                              <1> 	;	EDX = physical address of the page frame
  2397                              <1> 	;	      (with attribute bits)
  2398                              <1> 	;	ECX = byte count within the page frame
  2399                              <1> 	;
  2400                              <1> 	; Modified Registers -> EAX, EBX, ECX, EDX
  2401                              <1> 	;
  2402 000059FA 81C300004000        <1> 	add	ebx, CORE ; 18/10/2015
  2403                              <1> get_physical_addr_x: ; 27/05/2016
  2404 00005A00 A1[B8030300]        <1> 	mov	eax, [u.pgdir]
  2405 00005A05 E8F6F9FFFF          <1> 	call	get_pte
  2406                              <1> 		; EDX = Page table entry address (if CF=0)
  2407                              <1> 	        ;       Page directory entry address (if CF=1)
  2408                              <1> 		;       (Bit 0 value is 0 if PT is not present)
  2409                              <1> 		; EAX = Page table entry value (page address)
  2410                              <1> 		;	CF = 1 -> PDE not present or invalid ? 
  2411 00005A0A 731C                <1> 	jnc	short gpa_1
  2412                              <1> 	;
  2413 00005A0C E8D4F8FFFF          <1> 	call	allocate_page
  2414 00005A11 7248                <1> 	jc	short gpa_im_err  ; 'insufficient memory' error
  2415                              <1> gpa_0:
  2416 00005A13 E847F9FFFF          <1> 	call 	clear_page
  2417                              <1> 	; EAX = Physical (base) address of the allocated (new) page
  2418 00005A18 0C07                <1> 	or	al, PDE_A_PRESENT + PDE_A_WRITE + PDE_A_USER ; 4+2+1 = 7
  2419                              <1> 			   ; lower 3 bits are used as U/S, R/W, P flags
  2420                              <1> 			   ; (user, writable, present page)	
  2421 00005A1A 8902                <1> 	mov	[edx], eax ; Let's put the new page directory entry here !
  2422 00005A1C A1[B8030300]        <1> 	mov	eax, [u.pgdir]	
  2423 00005A21 E8DAF9FFFF          <1> 	call	get_pte
  2424 00005A26 7233                <1> 	jc	short gpa_im_err ; 'insufficient memory' error
  2425                              <1> gpa_1:
  2426                              <1> 	; EAX = PTE value, EDX = PTE address
  2427 00005A28 A801                <1> 	test 	al, PTE_A_PRESENT
  2428 00005A2A 751F                <1> 	jnz	short gpa_3 ; 26/03/2017
  2429 00005A2C 09C0                <1> 	or	eax, eax
  2430 00005A2E 7456                <1> 	jz	short gpa_7  ; Allocate a new page
  2431                              <1> 	; 20/07/2015
  2432 00005A30 55                  <1> 	push	ebp
  2433 00005A31 89DD                <1> 	mov	ebp, ebx ; virtual (linear) address
  2434                              <1> 	; reload swapped page
  2435 00005A33 E878000000          <1> 	call	reload_page ; 28/04/2015
  2436 00005A38 5D                  <1> 	pop	ebp
  2437 00005A39 724A                <1> 	jc	short gpa_retn
  2438                              <1> gpa_2:
  2439                              <1> 	; 26/03/2017
  2440                              <1> 	; 20/02/2017
  2441                              <1> 	; If a page will contain a Signal Response Byte
  2442                              <1> 	; it must not be swapped out, because
  2443                              <1> 	; timer service or irq callback service
  2444                              <1> 	; will write a signal return/response byte 
  2445                              <1> 	; directly by using physical address of Signal
  2446                              <1> 	; Response Byte.(Even if process is not running,
  2447                              <1> 	; or it is running with swapped out pages.)
  2448                              <1> 	;
  2449                              <1> 	; 'no_page_swap' will be set by 'systimer' or
  2450                              <1> 	; 'syscalbac' sistem functions/calls. (*)
  2451                              <1> 	;
  2452 00005A3B 803D[52700100]00    <1> 	cmp	byte [no_page_swap], 0
  2453 00005A42 761D                <1> 	jna	short gpa_4 ; this page can be swapped out
  2454                              <1> 	; this page must not be swapped out
  2455                              <1> 	; but 'no_page_swap' must be reset here
  2456                              <1> 	; imediately for other callers (*)
  2457                              <1> 	; (otherwise, swap queue would not be long enough) 
  2458 00005A44 E84B000000          <1> 	call	gpa_8 ; 26/03/2017
  2459 00005A49 EB1D                <1> 	jmp	short gpa_5
  2460                              <1> gpa_3: 
  2461                              <1> 	; 26/03/2017
  2462 00005A4B 803D[52700100]00    <1> 	cmp	byte [no_page_swap], 0
  2463 00005A52 7618                <1> 	jna	short gpa_6 ; this page can be swapped out
  2464 00005A54 E83B000000          <1> 	call	gpa_8
  2465 00005A59 EB11                <1> 	jmp	short gpa_6
  2466                              <1> 
  2467                              <1> gpa_im_err:	
  2468 00005A5B B804000000          <1> 	mov	eax, ERR_MINOR_IM ; Insufficient memory (minor) error!
  2469                              <1> 				  ; Major error = 0 (No protection fault)	
  2470 00005A60 C3                  <1> 	retn
  2471                              <1> gpa_4:
  2472                              <1> 	; 20/07/2015
  2473                              <1> 	; 20/05/2015
  2474                              <1> 	; add this page to swap queue
  2475 00005A61 50                  <1> 	push	eax 
  2476                              <1> 	; EBX = Linear (CORE+virtual) address ; 20/02/2017 
  2477 00005A62 E8BDFEFFFF          <1> 	call 	add_to_swap_queue
  2478 00005A67 58                  <1> 	pop	eax
  2479                              <1> gpa_5:
  2480                              <1> 		; PTE address in EDX
  2481                              <1> 		; virtual address in EBX
  2482                              <1> 	; EAX = memory page address
  2483 00005A68 0C07                <1> 	or	al, PTE_A_PRESENT + PTE_A_USER + PTE_A_WRITE
  2484                              <1> 				  ; present flag, bit 0 = 1
  2485                              <1> 				  ; user flag, bit 2 = 1	
  2486                              <1> 				  ; writable flag, bit 1 = 1
  2487 00005A6A 8902                <1> 	mov	[edx], eax  ; Update PTE value
  2488                              <1> gpa_6:
  2489                              <1> 	; 18/10/2015
  2490 00005A6C 89D9                <1> 	mov	ecx, ebx
  2491 00005A6E 81E1FF0F0000        <1> 	and	ecx, PAGE_OFF
  2492 00005A74 89C2                <1> 	mov 	edx, eax
  2493 00005A76 662500F0            <1> 	and	ax, PTE_A_CLEAR
  2494 00005A7A 01C8                <1> 	add	eax, ecx
  2495 00005A7C F7D9                <1> 	neg	ecx ; 1 -> -1 (0FFFFFFFFh), 4095 (0FFFh) -> -4095
  2496 00005A7E 81C100100000        <1> 	add	ecx, PAGE_SIZE
  2497 00005A84 F8                  <1> 	clc
  2498                              <1> gpa_retn:
  2499 00005A85 C3                  <1> 	retn
  2500                              <1> gpa_7:	
  2501 00005A86 E85AF8FFFF          <1> 	call	allocate_page
  2502 00005A8B 72CE                <1> 	jc	short gpa_im_err ; 'insufficient memory' error
  2503 00005A8D E8CDF8FFFF          <1> 	call	clear_page
  2504 00005A92 EBA7                <1> 	jmp	short gpa_2
  2505                              <1> 
  2506                              <1> gpa_8: ; 26/03/2017
  2507 00005A94 C605[52700100]00    <1> 	mov	byte [no_page_swap], 0
  2508 00005A9B 53                  <1> 	push	ebx
  2509 00005A9C 50                  <1> 	push	eax ; 26/03/2017
  2510 00005A9D 6681E300F0          <1>         and     bx, ~PAGE_OFF ; ~0FFFh ; reset bits, 0 to 11
  2511 00005AA2 8A1D[B3030300]      <1> 	mov	bl, [u.uno] ; current process number
  2512 00005AA8 E89DFDFFFF          <1> 	call	swap_queue_shift ; drop from the queue if
  2513                              <1> 				 ; it is already on the queue
  2514 00005AAD 58                  <1> 	pop	eax ; 26/03/2017
  2515 00005AAE 5B                  <1> 	pop	ebx
  2516 00005AAF C3                  <1> 	retn
  2517                              <1> 
  2518                              <1> reload_page:
  2519                              <1> 	; 20/07/2015
  2520                              <1> 	; 28/04/2015 (Retro UNIX 386 v1 - beginning)
  2521                              <1> 	;
  2522                              <1> 	; Reload (Restore) swapped page at memory
  2523                              <1> 	;
  2524                              <1> 	; INPUT -> 
  2525                              <1> 	;	EBP = Virtual (linear) memory address
  2526                              <1> 	;	EAX = PTE value (swap disk sector address)
  2527                              <1> 	;	(Swap disk sector address = bit 1 to bit 31 of EAX)	
  2528                              <1> 	; OUTPUT ->
  2529                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS OF RELOADED PAGE
  2530                              <1> 	;
  2531                              <1> 	;	CF = 1 and EAX = error code
  2532                              <1> 	;
  2533                              <1> 	; Modified Registers -> none (except EAX)
  2534                              <1> 	;
  2535 00005AB0 D1E8                <1> 	shr	eax, 1   ; Convert PTE value to swap disk address 
  2536 00005AB2 53                  <1> 	push	ebx      ;
  2537 00005AB3 89C3                <1> 	mov	ebx, eax ; Swap disk (offset) address	
  2538 00005AB5 E82BF8FFFF          <1> 	call	allocate_page
  2539 00005ABA 720C                <1> 	jc	short rlp_im_err
  2540 00005ABC 93                  <1> 	xchg 	eax, ebx	
  2541                              <1> 	; EBX = Physical memory (page) address
  2542                              <1> 	; EAX = Swap disk (offset) address
  2543                              <1> 	; EBP = Virtual (linear) memory address
  2544 00005ABD E862FCFFFF          <1> 	call	swap_in
  2545 00005AC2 720B                <1> 	jc	short rlp_swp_err  ; (swap disk/file read error)
  2546 00005AC4 89D8                <1> 	mov	eax, ebx	
  2547                              <1> rlp_retn:
  2548 00005AC6 5B                  <1> 	pop	ebx
  2549 00005AC7 C3                  <1> 	retn
  2550                              <1> 	
  2551                              <1> rlp_im_err:	
  2552 00005AC8 B804000000          <1> 	mov	eax, ERR_MINOR_IM ; Insufficient memory (minor) error!
  2553                              <1> 				  ; Major error = 0 (No protection fault)	
  2554 00005ACD EBF7                <1> 	jmp	short rlp_retn
  2555                              <1> 
  2556                              <1> rlp_swp_err:
  2557 00005ACF B828000000          <1> 	mov 	eax, SWP_DISK_READ_ERR ; Swap disk read error !
  2558 00005AD4 EBF0                <1> 	jmp	short rlp_retn
  2559                              <1> 
  2560                              <1> 
  2561                              <1> copy_page_dir:
  2562                              <1> 	; 19/09/2015
  2563                              <1> 	; temporary - 07/09/2015
  2564                              <1> 	; 07/09/2015 (Retro UNIX 386 v1 - beginning)
  2565                              <1> 	;
  2566                              <1> 	; INPUT -> 
  2567                              <1> 	;	[u.pgdir] = PHYSICAL (real/flat) ADDRESS of the parent's
  2568                              <1> 	;		    page directory.
  2569                              <1> 	; OUTPUT ->
  2570                              <1> 	;	EAX =  PHYSICAL (real/flat) ADDRESS of the child's
  2571                              <1> 	;	       page directory.
  2572                              <1> 	;	(New page directory with new page table entries.)
  2573                              <1> 	;	(New page tables with read only copies of the parent's
  2574                              <1> 	;	pages.)
  2575                              <1> 	;	EAX = 0 -> Error (CF = 1)
  2576                              <1> 	;
  2577                              <1> 	; Modified Registers -> none (except EAX)
  2578                              <1> 	;
  2579 00005AD6 E80AF8FFFF          <1> 	call	allocate_page
  2580 00005ADB 723E                <1> 	jc	short cpd_err
  2581                              <1> 	;
  2582 00005ADD 55                  <1> 	push	ebp ; 20/07/2015
  2583 00005ADE 56                  <1> 	push	esi
  2584 00005ADF 57                  <1> 	push	edi
  2585 00005AE0 53                  <1> 	push	ebx
  2586 00005AE1 51                  <1> 	push	ecx
  2587 00005AE2 8B35[B8030300]      <1> 	mov	esi, [u.pgdir]
  2588 00005AE8 89C7                <1> 	mov	edi, eax
  2589 00005AEA 50                  <1> 	push	eax ; save child's page directory address
  2590                              <1> 	; copy PDE 0 from the parent's page dir to the child's page dir
  2591                              <1> 	; (use same system space for all user page tables) 
  2592 00005AEB A5                  <1> 	movsd
  2593 00005AEC BD00004000          <1> 	mov	ebp, 1024*4096 ; pass the 1st 4MB (system space)
  2594 00005AF1 B9FF030000          <1> 	mov	ecx, (PAGE_SIZE / 4) - 1 ; 1023
  2595                              <1> cpd_0:	
  2596 00005AF6 AD                  <1> 	lodsd
  2597                              <1> 	;or	eax, eax
  2598                              <1>         ;jnz     short cpd_1
  2599 00005AF7 A801                <1> 	test	al, PDE_A_PRESENT ;  bit 0 =  1
  2600 00005AF9 7508                <1> 	jnz	short cpd_1
  2601                              <1>  	; (virtual address at the end of the page table)	
  2602 00005AFB 81C500004000        <1> 	add	ebp, 1024*4096 ; page size * PTE count
  2603 00005B01 EB0F                <1> 	jmp	short cpd_2
  2604                              <1> cpd_1:	
  2605 00005B03 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear attribute bits
  2606 00005B07 89C3                <1> 	mov	ebx, eax
  2607                              <1> 	; EBX = Parent's page table address
  2608 00005B09 E81F000000          <1> 	call	copy_page_table
  2609 00005B0E 720C                <1> 	jc	short cpd_p_err
  2610                              <1> 	; EAX = Child's page table address
  2611 00005B10 0C07                <1> 	or	al, PDE_A_PRESENT + PDE_A_WRITE + PDE_A_USER
  2612                              <1> 			 ; set bit 0, bit 1 and bit 2 to 1
  2613                              <1> 			 ; (present, writable, user)
  2614                              <1> cpd_2:
  2615 00005B12 AB                  <1> 	stosd
  2616 00005B13 E2E1                <1> 	loop	cpd_0
  2617                              <1> 	;
  2618 00005B15 58                  <1> 	pop	eax  ; restore child's page directory address
  2619                              <1> cpd_3:
  2620 00005B16 59                  <1> 	pop	ecx
  2621 00005B17 5B                  <1> 	pop	ebx
  2622 00005B18 5F                  <1> 	pop	edi
  2623 00005B19 5E                  <1> 	pop	esi
  2624 00005B1A 5D                  <1> 	pop	ebp
  2625                              <1> cpd_err:
  2626 00005B1B C3                  <1> 	retn
  2627                              <1> cpd_p_err:
  2628                              <1> 	; release the allocated pages missing (recover free space)
  2629 00005B1C 58                  <1> 	pop	eax  ; the new page directory address (physical)
  2630 00005B1D 8B1D[B8030300]      <1> 	mov	ebx, [u.pgdir] ; parent's page directory address 
  2631 00005B23 E8F6F8FFFF          <1> 	call 	deallocate_page_dir
  2632 00005B28 29C0                <1> 	sub	eax, eax ; 0
  2633 00005B2A F9                  <1> 	stc
  2634 00005B2B EBE9                <1> 	jmp	short cpd_3	
  2635                              <1> 
  2636                              <1> copy_page_table:
  2637                              <1> 	; 19/09/2015
  2638                              <1> 	; temporary - 07/09/2015
  2639                              <1> 	; 07/09/2015 (Retro UNIX 386 v1 - beginning)
  2640                              <1> 	;
  2641                              <1> 	; INPUT -> 
  2642                              <1> 	;	EBX = PHYSICAL (real/flat) ADDRESS of the parent's page table.
  2643                              <1> 	;	EBP = page table entry index (from 'copy_page_dir')
  2644                              <1> 	; OUTPUT ->
  2645                              <1> 	;	EAX = PHYSICAL (real/flat) ADDRESS of the child's page table.
  2646                              <1> 	;	EBP = (recent) page table index (for 'add_to_swap_queue')	
  2647                              <1> 	;	CF = 1 -> error 
  2648                              <1> 	;
  2649                              <1> 	; Modified Registers -> EBP (except EAX)
  2650                              <1> 	;
  2651 00005B2D E8B3F7FFFF          <1> 	call	allocate_page
  2652 00005B32 725A                <1> 	jc	short cpt_err
  2653                              <1> 	;
  2654 00005B34 50                  <1> 	push	eax ; *
  2655                              <1> 	;push 	ebx
  2656 00005B35 56                  <1> 	push	esi
  2657 00005B36 57                  <1> 	push	edi
  2658 00005B37 52                  <1> 	push	edx
  2659 00005B38 51                  <1> 	push	ecx
  2660                              <1> 	;
  2661 00005B39 89DE                <1> 	mov	esi, ebx
  2662 00005B3B 89C7                <1> 	mov	edi, eax
  2663 00005B3D 89C2                <1> 	mov	edx, eax
  2664 00005B3F 81C200100000        <1> 	add	edx, PAGE_SIZE 	
  2665                              <1> cpt_0:
  2666 00005B45 AD                  <1> 	lodsd
  2667 00005B46 A801                <1> 	test	al, PTE_A_PRESENT ;  bit 0 =  1
  2668 00005B48 750B                <1> 	jnz	short cpt_1
  2669 00005B4A 21C0                <1> 	and	eax, eax
  2670 00005B4C 7430                <1> 	jz	short cpt_2
  2671                              <1> 	; ebp = virtual (linear) address of the memory page
  2672 00005B4E E85DFFFFFF          <1> 	call	reload_page ; 28/04/2015
  2673 00005B53 7234                <1> 	jc	short cpt_p_err
  2674                              <1> cpt_1:
  2675 00005B55 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; clear attribute bits
  2676 00005B59 89C1                <1> 	mov	ecx, eax
  2677                              <1> 	; Allocate a new page for the child process
  2678 00005B5B E885F7FFFF          <1> 	call	allocate_page
  2679 00005B60 7227                <1> 	jc	short cpt_p_err
  2680 00005B62 57                  <1> 	push	edi
  2681 00005B63 56                  <1> 	push	esi
  2682 00005B64 89CE                <1> 	mov	esi, ecx
  2683 00005B66 89C7                <1> 	mov	edi, eax
  2684 00005B68 B900040000          <1> 	mov	ecx, PAGE_SIZE/4
  2685 00005B6D F3A5                <1> 	rep	movsd	; copy page (4096 bytes)
  2686 00005B6F 5E                  <1> 	pop	esi
  2687 00005B70 5F                  <1> 	pop	edi
  2688                              <1> 	; 
  2689 00005B71 53                  <1> 	push	ebx
  2690 00005B72 50                  <1> 	push	eax
  2691 00005B73 89EB                <1> 	mov	ebx, ebp
  2692                              <1> 	; ebx = virtual address of the memory page
  2693 00005B75 E8AAFDFFFF          <1> 	call	add_to_swap_queue
  2694 00005B7A 58                  <1> 	pop	eax
  2695 00005B7B 5B                  <1> 	pop	ebx
  2696                              <1> 	;
  2697                              <1> 	;or	ax, PTE_A_USER+PTE_A_PRESENT 
  2698 00005B7C 0C07                <1> 	or	al, PTE_A_USER+PTE_A_WRITE+PTE_A_PRESENT 
  2699                              <1> cpt_2:
  2700 00005B7E AB                  <1> 	stosd  ; EDI points to child's PTE  	 
  2701                              <1> 	;
  2702 00005B7F 81C500100000        <1> 	add	ebp, 4096 ; 20/07/2015 (next page)
  2703                              <1> 	;
  2704 00005B85 39D7                <1> 	cmp	edi, edx
  2705 00005B87 72BC                <1> 	jb	short cpt_0
  2706                              <1> cpt_p_err:
  2707 00005B89 59                  <1> 	pop	ecx
  2708 00005B8A 5A                  <1> 	pop	edx
  2709 00005B8B 5F                  <1> 	pop	edi
  2710 00005B8C 5E                  <1> 	pop	esi
  2711                              <1> 	;pop	ebx
  2712 00005B8D 58                  <1> 	pop	eax ; *
  2713                              <1> cpt_err:
  2714 00005B8E C3                  <1> 	retn
  2715                              <1> 
  2716                              <1> allocate_memory_block:
  2717                              <1> 	; 01/05/2017
  2718                              <1> 	; 28/04/2017
  2719                              <1> 	; 25/04/2017
  2720                              <1> 	; 01/04/2016, 02/04/2016, 03/04/2016
  2721                              <1> 	; 13/03/2016, 14/03/2016
  2722                              <1> 	; 12/03/2016 (TRDOS 386 = TRDOS v2.0)
  2723                              <1> 	; Allocating contiguous memory pages (in the kernel's memory space)
  2724                              <1> 	;
  2725                              <1> 	; INPUT -> 
  2726                              <1> 	;	EAX = Beginning address (physical)
  2727                              <1> 	;	EAX = 0 -> Allocate memory block from the first proper aperture	
  2728                              <1> 	;	ECX = Number of bytes to be allocated
  2729                              <1> 	;
  2730                              <1> 	; OUTPUT ->
  2731                              <1> 	; 	1) cf = 0 -> successful
  2732                              <1> 	;	EAX = Beginning (physical) address of the allocated memory block
  2733                              <1> 	;	ECX = Number of allocated bytes (rounded up to page borders) 
  2734                              <1> 	;	2) cf = 1 -> unsuccessful
  2735                              <1> 	;	 2.1) If EAX > 0 -> 
  2736                              <1> 	;	      (Number of requested pages is more than # of free pages
  2737                              <1> 	;	       but contiguous free pages -the aperture- is not enough!)	   	
  2738                              <1> 	;	      EAX = Beginning address of available aperture
  2739                              <1> 	;		    (one of all aperture with max. aperture size/length)		
  2740                              <1> 	;	      ECX = Size of available aperture (memory block) in bytes
  2741                              <1> 	;	 2.2) If EAX = 0 -> Out of memory error 
  2742                              <1> 	;	            (number of free pages is less than requested number)
  2743                              <1> 	;	      ECX = Total number of free bytes (free pages * 4096) 
  2744                              <1> 	;		    (It is not number of contiguous free bytes)	
  2745                              <1> 	;
  2746                              <1> 	; (Modified Registers -> EAX, ECX)
  2747                              <1> 	;
  2748                              <1> 	; PURPOSE: Loading a file at memory for copying or running etc.
  2749                              <1> 	; If this procedure returns with cf is set, ECX contains maximum
  2750                              <1> 	; available space and EAX contains the beginning address of it.
  2751                              <1> 	; If EAX has zero, ECX contains total number of free bytes.
  2752                              <1> 	; If requested block has been successfully allocated (by rounding up to
  2753                              <1> 	; the last page border), it must be deallocated later by using
  2754                              <1> 	; 'deallocate_memory_block' procedure.    
  2755                              <1> 
  2756 00005B8F 52                  <1> 	push	edx ; *
  2757 00005B90 BAFF0F0000          <1> 	mov	edx, PAGE_SIZE - 1   ; 4095
  2758 00005B95 01D0                <1> 	add	eax, edx
  2759 00005B97 01D1                <1> 	add	ecx, edx
  2760 00005B99 C1E90C              <1> 	shr	ecx, PAGE_SHIFT	     ; 12
  2761                              <1> 
  2762                              <1> 	; ECX = number of contiguous pages to be allocated
  2763 00005B9C 8B15[885E0100]      <1> 	mov	edx, [free_pages]
  2764                              <1> 	; 01/05/2017
  2765                              <1> 	;or	ecx, ecx
  2766                              <1> 	;jz	short amb3
  2767                              <1> 	; If ECX=0, set cf to 1 and return with max. available mem block size
  2768                              <1> 
  2769 00005BA2 39D1                <1> 	cmp	ecx, edx
  2770 00005BA4 7760                <1> 	ja	short amb_3
  2771                              <1> 
  2772 00005BA6 C1E80C              <1> 	shr	eax, PAGE_SHIFT      ; 12
  2773                              <1> 
  2774 00005BA9 89C2                <1> 	mov	edx, eax 	     ; page number
  2775 00005BAB C1EA03              <1> 	shr	edx, 3		     ; to get offset to M.A.T.
  2776                              <1> 				     ; (1 allocation bit = 1 page)
  2777                              <1> 				     ; (1 allocation bytes = 8 pages)
  2778 00005BAE 80E2FC              <1> 	and	dl, 0FCh 	     ; clear lower 2 bits
  2779                              <1> 				     ; (to get 32 bit position)	
  2780 00005BB1 53                  <1> 	push	ebx ; **
  2781                              <1> amb_0:
  2782 00005BB2 890D[3C6A0100]      <1> 	mov	[mem_ipg_count], ecx ; initial (reset) value of page count
  2783 00005BB8 890D[406A0100]      <1> 	mov	[mem_pg_count], ecx
  2784 00005BBE 31C9                <1> 	xor	ecx, ecx ; 0
  2785 00005BC0 890D[446A0100]      <1> 	mov	[mem_aperture], ecx ; 0
  2786 00005BC6 890D[486A0100]      <1> 	mov	[mem_max_aperture], ecx ; 0
  2787                              <1> 	
  2788 00005BCC BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL   ; Memory Allocation Table address.
  2789 00005BD1 3B15[8C5E0100]      <1> 	cmp	edx, [next_page]     ; Is the beginning page address lower
  2790                              <1> 				     ; than the address in 'next_page' ?
  2791                              <1> 				     ; (the first/next free page of user space)		
  2792 00005BD7 7208                <1> 	jb	short amb_1
  2793 00005BD9 3B15[905E0100]      <1> 	cmp 	edx, [last_page]     ; is the beginning page address higher
  2794                              <1> 				     ; than the address in 'last_page' ?
  2795                              <1> 				     ; (end of the memory)		
  2796 00005BDF 7606                <1> 	jna	short amb_2	     ; no	
  2797                              <1> amb_1:
  2798 00005BE1 8B15[8C5E0100]      <1> 	mov	edx, [next_page]     ; M.A.T. offset (1 M.A.T. byte = 8 pages)
  2799                              <1> amb_2:
  2800 00005BE7 01D3                <1> 	add	ebx, edx
  2801                              <1> 
  2802                              <1> 	; 28/04/2017
  2803                              <1> 	;xor	ecx, ecx
  2804 00005BE9 0FBC0B              <1> 	bsf	ecx, [ebx]	     ; 0 to 31
  2805 00005BEC 89D0                <1> 	mov	eax, edx
  2806 00005BEE C1E003              <1> 	shl	eax, 3		     ; *8	
  2807 00005BF1 01C8                <1> 	add	eax, ecx	     ; beginning page number
  2808                              <1> 
  2809 00005BF3 A3[4C6A0100]        <1> 	mov	[mem_pg_pos], eax    ; beginning page no (for curr. mem. aperture)
  2810 00005BF8 A3[506A0100]        <1>  	mov	[mem_max_pg_pos], eax ; beginning page no for max. mem. aperture
  2811                              <1> 
  2812 00005BFD 83E01F              <1> 	and	eax, 1Fh	     ; lower 5 bits only (0 to 31)
  2813                              <1> 				     ; (allocation bit position)	 
  2814 00005C00 750E                <1> 	jnz	short amb_4	     ; 0
  2815 00005C02 B120                <1> 	mov	cl, 32
  2816 00005C04 EB4B                <1> 	jmp	short amb_10
  2817                              <1> 
  2818                              <1> amb_3:	; out_of_memory
  2819 00005C06 31C0                <1> 	xor	eax, eax ; 0
  2820 00005C08 89D1                <1> 	mov	ecx, edx ; free pages
  2821 00005C0A C1E10C              <1> 	shl	ecx, PAGE_SHIFT
  2822 00005C0D 5A                  <1> 	pop	edx ; *
  2823 00005C0E F9                  <1> 	stc
  2824 00005C0F C3                  <1> 	retn	
  2825                              <1> amb_4:
  2826 00005C10 8B13                <1> 	mov	edx, [ebx]
  2827 00005C12 88C1                <1> 	mov	cl, al ; 1 to 31
  2828 00005C14 D3EA                <1> 	shr	edx, cl
  2829 00005C16 89D0                <1> 	mov	eax, edx
  2830                              <1> amb_5:
  2831 00005C18 D1E8                <1> 	shr	eax, 1 ; (***)
  2832 00005C1A 7317                <1> 	jnc	short amb_7
  2833 00005C1C FF05[446A0100]      <1> 	inc	dword [mem_aperture]
  2834 00005C22 FF0D[406A0100]      <1> 	dec	dword [mem_pg_count]
  2835 00005C28 7470                <1> 	jz	short amb_15
  2836                              <1> amb_6:
  2837                              <1> 	; 28/04/2017
  2838 00005C2A FEC1                <1> 	inc	cl
  2839 00005C2C 80F920              <1> 	cmp	cl, 32
  2840 00005C2F 730D                <1> 	jnb	short amb_9
  2841 00005C31 EBE5                <1> 	jmp	short amb_5
  2842                              <1> amb_7:
  2843 00005C33 50                  <1> 	push	eax ; (***) allocation bits (in shifted status)
  2844 00005C34 E81B010000          <1> 	call	amb_26 ; set maximum memory aperture (free memory block size)
  2845 00005C39 58                  <1> 	pop	eax ; (***)
  2846 00005C3A EBEE                <1> 	jmp	short amb_6
  2847                              <1> amb_8:
  2848                              <1> 	; 28/04/2017
  2849 00005C3C B120                <1> 	mov	cl, 32
  2850                              <1> amb_9:
  2851 00005C3E 89DA                <1> 	mov	edx, ebx
  2852 00005C40 81EA00001000        <1> 	sub	edx, MEM_ALLOC_TBL
  2853 00005C46 3B15[905E0100]      <1> 	cmp	edx, [last_page]
  2854 00005C4C 7336                <1> 	jnb	short amb_14 ; contiguous pages not enough
  2855 00005C4E 83C304              <1> 	add	ebx, 4
  2856                              <1> amb_10:
  2857 00005C51 8B03                <1> 	mov	eax, [ebx]
  2858 00005C53 21C0                <1> 	and 	eax, eax
  2859 00005C55 7408                <1>         jz      short amb_11 ; there is not a free page bit in this alloc dword
  2860 00005C57 40                  <1> 	inc	eax ; 0FFFFFFFFh -> 0
  2861 00005C58 740C                <1> 	jz	short amb_12 ; all of bits are set (32 free pages)
  2862 00005C5A 48                  <1> 	dec	eax
  2863 00005C5B 28C9                <1> 	sub	cl, cl ; 0
  2864 00005C5D EBB9                <1> 	jmp	short amb_5
  2865                              <1> amb_11:
  2866 00005C5F E8F0000000          <1> 	call	amb_26 ; set maximum memory aperture (free memory block size)
  2867 00005C64 EBD8                <1> 	jmp	short amb_9	
  2868                              <1> amb_12:
  2869 00005C66 390D[406A0100]      <1> 	cmp	[mem_pg_count], ecx ; 32
  2870 00005C6C 7306                <1> 	jnb	short amb_13
  2871 00005C6E 8B0D[406A0100]      <1> 	mov	ecx, [mem_pg_count]
  2872                              <1> amb_13:
  2873 00005C74 010D[446A0100]      <1> 	add	[mem_aperture], ecx
  2874 00005C7A 290D[406A0100]      <1> 	sub	[mem_pg_count], ecx
  2875 00005C80 7618                <1> 	jna	short amb_15
  2876 00005C82 EBBA                <1> 	jmp	short amb_9 ; 01/05/2017
  2877                              <1> amb_14:
  2878 00005C84 E8CB000000          <1> 	call	amb_26 ; 28/04/2017
  2879 00005C89 A1[506A0100]        <1> 	mov	eax, [mem_max_pg_pos] ; begin address of max. mem aperture	
  2880 00005C8E 8B0D[486A0100]      <1> 	mov	ecx, [mem_max_aperture] ; max. (largest) memory aperture
  2881 00005C94 F9                  <1> 	stc
  2882 00005C95 E9AF000000          <1>         jmp     amb_25
  2883                              <1> 
  2884                              <1> amb_15: ; OK !
  2885 00005C9A A1[4C6A0100]        <1> 	mov	eax, [mem_pg_pos]    ; Beginning address as page number
  2886 00005C9F 8B0D[446A0100]      <1> 	mov	ecx, [mem_aperture]  ; Free contiguous page count (>=1)
  2887                              <1> amb_16:
  2888                              <1> 	; allocate contiguous memory pages (via memory allocation table bits)
  2889 00005CA5 89C2                <1> 	mov	edx, eax
  2890                              <1> 	; 25/04/2017
  2891 00005CA7 C1EA03              <1> 	shr	edx, 3		 ; 8 pages in one allocation byte
  2892 00005CAA 80E2FC              <1> 	and	dl, 0FCh	 ; clear lower 2 bits
  2893                              <1> 				 ; (for dword/32bit positioning)	
  2894                              <1> 
  2895 00005CAD BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL
  2896 00005CB2 01D3                <1> 	add	ebx, edx
  2897 00005CB4 83E01F              <1> 	and	eax, 1Fh ; 31
  2898                              <1> 	; 03/04/2016
  2899 00005CB7 BA20000000          <1> 	mov	edx, 32
  2900 00005CBC 28C2                <1> 	sub	dl, al
  2901 00005CBE 39CA                <1> 	cmp	edx, ecx	 ; ecx >= 1
  2902 00005CC0 7602                <1> 	jna	short amb_17
  2903 00005CC2 89CA                <1> 	mov	edx, ecx
  2904                              <1> amb_17:
  2905 00005CC4 29D1                <1> 	sub	ecx, edx
  2906 00005CC6 51                  <1> 	push	ecx ; ***
  2907 00005CC7 89D1                <1> 	mov	ecx, edx
  2908                              <1> amb_18:		
  2909 00005CC9 0FB303              <1> 	btr	[ebx], eax	 ; The destination bit indexed by the source value
  2910                              <1> 				 ; is copied into the Carry Flag and then cleared
  2911                              <1> 				 ; in the destination.
  2912 00005CCC FF0D[885E0100]      <1> 	dec     dword [free_pages] ; 1 page has been allocated (X = X-1) 
  2913 00005CD2 49                  <1> 	dec	ecx
  2914 00005CD3 7404                <1> 	jz	short amb_19
  2915 00005CD5 FEC0                <1> 	inc	al
  2916 00005CD7 EBF0                <1> 	jmp	short amb_18
  2917                              <1> amb_19:	
  2918 00005CD9 59                  <1> 	pop	ecx ; ***
  2919 00005CDA 21C9                <1> 	and	ecx, ecx ; 0 ?
  2920 00005CDC 741E                <1> 	jz	short amb_22	
  2921                              <1> 	; 01/04/2016
  2922 00005CDE B020                <1> 	mov	al, 32
  2923                              <1> amb_20:
  2924 00005CE0 83C304              <1> 	add	ebx, 4
  2925 00005CE3 39C1                <1> 	cmp	ecx, eax ; 32
  2926 00005CE5 7305                <1> 	jnb	short amb_21
  2927                              <1> 	; ECX < 32
  2928 00005CE7 28C0                <1> 	sub	al, al ; 0
  2929 00005CE9 50                  <1> 	push	eax ; 0 ***
  2930 00005CEA EBDD                <1> 	jmp	short amb_18
  2931                              <1> amb_21:
  2932 00005CEC 2905[885E0100]      <1> 	sub	[free_pages], eax   ; [free_pages] = [free_pages] - 32
  2933 00005CF2 C70300000000        <1> 	mov	dword [ebx], 0	    ; reset 32 bits
  2934 00005CF8 29C1                <1> 	sub	ecx, eax ; 32
  2935 00005CFA 75E4                <1> 	jnz	short amb_20
  2936                              <1> amb_22:
  2937 00005CFC A1[4C6A0100]        <1> 	mov	eax, [mem_pg_pos]   ; Beginning address as page number
  2938 00005D01 8B0D[446A0100]      <1> 	mov	ecx, [mem_aperture] ; Free contiguous page count
  2939                              <1> 	; [next_page] update
  2940 00005D07 89C2                <1> 	mov	edx, eax
  2941                              <1> 	; 03/04/2016
  2942 00005D09 C1EA03              <1> 	shr	edx, 3		     ; to get offset to M.A.T.
  2943                              <1> 				     ; (1 allocation bit = 1 page)
  2944                              <1> 				     ; (1 allocation bytes = 8 pages)
  2945 00005D0C 80E2FC              <1> 	and	dl, 0FCh 	     ; clear lower 2 bits
  2946                              <1> 				     ; (to get 32 bit position)	
  2947 00005D0F 3B15[8C5E0100]      <1> 	cmp	edx, [next_page] ; first free page pointer offset
  2948 00005D15 7732                <1> 	ja	short amb_25
  2949 00005D17 BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL
  2950 00005D1C 833C1300            <1> 	cmp	dword [ebx+edx], 0
  2951 00005D20 7721                <1> 	ja	short amb_24
  2952 00005D22 89C2                <1> 	mov	edx, eax
  2953 00005D24 01CA                <1> 	add	edx, ecx
  2954 00005D26 C1EA03              <1> 	shr	edx, 3
  2955 00005D29 80E2FC              <1> 	and	dl, 0FCh
  2956                              <1> amb_23:
  2957 00005D2C 833C1300            <1> 	cmp	dword [ebx+edx], 0
  2958 00005D30 7711                <1> 	ja	short amb_24
  2959 00005D32 83C204              <1> 	add	edx, 4
  2960 00005D35 3B15[905E0100]      <1> 	cmp	edx, [last_page]    ; last page pointer offset
  2961 00005D3B 76EF                <1> 	jna	short amb_23
  2962 00005D3D 8B15[945E0100]      <1> 	mov	edx, [first_page]   ; (for) beginning of user's space
  2963                              <1> amb_24:
  2964 00005D43 8915[8C5E0100]      <1> 	mov	[next_page], edx
  2965                              <1> amb_25:
  2966 00005D49 9C                  <1> 	pushf
  2967 00005D4A C1E00C              <1> 	shl	eax, PAGE_SHIFT	     ; convert to phy. address in bytes
  2968 00005D4D C1E10C              <1> 	shl	ecx, PAGE_SHIFT	     ; convert to byte counts
  2969 00005D50 9D                  <1> 	popf
  2970 00005D51 5B                  <1> 	pop	ebx ; **
  2971 00005D52 5A                  <1> 	pop	edx ; *
  2972 00005D53 C3                  <1> 	retn
  2973                              <1> 
  2974                              <1> amb_26:	; set maximum free memory aperture (free memory block size) 
  2975 00005D54 89DA                <1> 	mov	edx, ebx ; current address
  2976 00005D56 81EA00001000        <1> 	sub	edx, MEM_ALLOC_TBL ; MAT beginning address
  2977                              <1> 	; 02/04/2016 
  2978 00005D5C C1E203              <1> 	shl	edx, 3 ; MAT byte offset * 8 = page number base
  2979 00005D5F 01CA                <1> 	add	edx, ecx ; current page number (ecx = 0 to 32)
  2980                              <1> 	;
  2981 00005D61 A1[446A0100]        <1> 	mov	eax, [mem_aperture]
  2982 00005D66 21C0                <1> 	and	eax, eax
  2983 00005D68 7421                <1>         jz      short amb_27
  2984 00005D6A C705[446A0100]0000- <1>         mov     dword [mem_aperture], 0
  2984 00005D72 0000                <1>
  2985 00005D74 3B05[486A0100]      <1> 	cmp	eax, [mem_max_aperture]
  2986 00005D7A 760F                <1> 	jna	short amb_27
  2987 00005D7C A3[486A0100]        <1> 	mov	[mem_max_aperture], eax
  2988                              <1> 	; 25/04/2017
  2989 00005D81 A1[4C6A0100]        <1> 	mov	eax, [mem_pg_pos]
  2990                              <1> 	; EAX = Beginning page number of the max. aperture 
  2991 00005D86 A3[506A0100]        <1> 	mov	[mem_max_pg_pos], eax
  2992                              <1> amb_27: 
  2993 00005D8B 8915[4C6A0100]      <1> 	mov	[mem_pg_pos], edx ; current page
  2994                              <1> 
  2995 00005D91 A1[3C6A0100]        <1> 	mov	eax, [mem_ipg_count] ; initial (reset) value of page count
  2996 00005D96 A3[406A0100]        <1> 	mov	[mem_pg_count], eax
  2997                              <1> 
  2998 00005D9B C3                  <1> 	retn
  2999                              <1> 
  3000                              <1> deallocate_memory_block:
  3001                              <1> 	; 03/04/2016
  3002                              <1> 	; 14/03/2016 (TRDOS 386 = TRDOS v2.0)
  3003                              <1> 	; Deallocating contiguous memory pages (in the kernel's memory space)
  3004                              <1> 	;
  3005                              <1> 	; INPUT -> 
  3006                              <1> 	;	EAX = Beginning address (physical)
  3007                              <1> 	;	ECX = Number of bytes to be deallocated
  3008                              <1> 	;
  3009                              <1> 	; OUTPUT ->
  3010                              <1> 	;	Memory Allocation Table bits will be updated
  3011                              <1> 	;	[free_pages] will be changed (increased)
  3012                              <1> 	;
  3013                              <1> 	; (Modified Registers -> EAX, ECX)
  3014                              <1> 	;
  3015                              <1> 	; PURPOSE: Unloading/Freeing a file -or an allocated memory block- 
  3016                              <1> 	; at memory after copying, running, saving, reading, writing etc.
  3017                              <1> 	;
  3018                              <1> 
  3019 00005D9C 52                  <1> 	push	edx ; *
  3020 00005D9D 53                  <1> 	push	ebx ; **
  3021                              <1> 
  3022 00005D9E C1E80C              <1> 	shr	eax, PAGE_SHIFT	     ; 12
  3023 00005DA1 C1E90C              <1> 	shr	ecx, PAGE_SHIFT	     ; 12
  3024                              <1> 
  3025                              <1> 	; EAX = Beginning page number
  3026                              <1> 	; ECX = Number of contiguous pages to be deallocated
  3027                              <1> damb_0:
  3028                              <1> 	; deallocate contiguous memory pages (via memory allocation table bits)
  3029 00005DA4 89C2                <1> 	mov	edx, eax
  3030 00005DA6 C1EA03              <1> 	shr	edx, 3		     ; to get offset to M.A.T.
  3031                              <1> 				     ; (1 allocation bit = 1 page)
  3032                              <1> 				     ; (1 allocation bytes = 8 pages)
  3033 00005DA9 80E2FC              <1> 	and	dl, 0FCh 	     ; clear lower 2 bits
  3034                              <1> 				     ; (to get 32 bit position)	
  3035 00005DAC 3B15[8C5E0100]      <1> 	cmp	edx, [next_page] ; next free page
  3036 00005DB2 7306                <1> 	jnb	short damb_1
  3037 00005DB4 8915[8C5E0100]      <1> 	mov	[next_page], edx
  3038                              <1> damb_1:
  3039 00005DBA BB00001000          <1> 	mov	ebx, MEM_ALLOC_TBL
  3040 00005DBF 01D3                <1> 	add	ebx, edx
  3041 00005DC1 83E01F              <1> 	and	eax, 1Fh ; 31
  3042                              <1> 
  3043                              <1> 	; 03/04/2016
  3044 00005DC4 BA20000000          <1> 	mov	edx, 32
  3045 00005DC9 28C2                <1> 	sub	dl, al
  3046 00005DCB 39CA                <1> 	cmp	edx, ecx
  3047 00005DCD 7602                <1> 	jna	short damb_2
  3048 00005DCF 89CA                <1> 	mov	edx, ecx
  3049                              <1> damb_2:
  3050 00005DD1 29D1                <1> 	sub	ecx, edx
  3051 00005DD3 51                  <1> 	push	ecx ; ***
  3052 00005DD4 89D1                <1> 	mov	ecx, edx
  3053                              <1> damb_3:		
  3054 00005DD6 0FAB03              <1> 	bts	[ebx], eax	     ; unlink/release/deallocate page
  3055                              <1> 				     ; set relevant bit to 1.
  3056                              <1> 				     ; set CF to the previous bit value	
  3057 00005DD9 FF05[885E0100]      <1> 	inc     dword [free_pages]   ; 1 page has been deallocated (X = X+1) 
  3058 00005DDF 49                  <1> 	dec	ecx
  3059 00005DE0 7404                <1> 	jz	short damb_4
  3060 00005DE2 FEC0                <1> 	inc	al
  3061 00005DE4 EBF0                <1> 	jmp	short damb_3
  3062                              <1> damb_4:	
  3063 00005DE6 59                  <1> 	pop	ecx ; ***
  3064 00005DE7 21C9                <1> 	and	ecx, ecx ; 0 ?
  3065 00005DE9 741E                <1> 	jz	short damb_7
  3066                              <1> 	; 03/04/2016
  3067 00005DEB B020                <1> 	mov	al, 32
  3068                              <1> damb_5:
  3069 00005DED 83C304              <1> 	add	ebx, 4
  3070 00005DF0 39C1                <1> 	cmp	ecx, eax ; 32
  3071 00005DF2 7305                <1> 	jnb	short damb_6
  3072                              <1> 	; ECX < 32
  3073 00005DF4 28C0                <1> 	sub	al, al ; 0
  3074 00005DF6 50                  <1> 	push	eax ; 0 ***
  3075 00005DF7 EBDD                <1> 	jmp	short damb_3
  3076                              <1> damb_6:
  3077 00005DF9 0105[885E0100]      <1> 	add	[free_pages], eax ; [free_pages] = [free_pages] + 32
  3078 00005DFF C703FFFFFFFF        <1> 	mov	dword [ebx], 0FFFFFFFFh ; set 32 bits
  3079 00005E05 29C1                <1> 	sub	ecx, eax ; 32
  3080 00005E07 75E4                <1> 	jnz	short damb_5
  3081                              <1> damb_7:
  3082 00005E09 5B                  <1> 	pop	ebx ; **
  3083 00005E0A 5A                  <1> 	pop	edx ; *
  3084 00005E0B C3                  <1> 	retn
  3085                              <1> 
  3086                              <1> direct_memory_access:
  3087                              <1> 	; 22/07/2017
  3088                              <1> 	; 12/05/2017
  3089                              <1> 	; 16/07/2016
  3090                              <1> 	; 12/07/2016 (TRDOS 386 = TRDOS v2.0)
  3091                              <1> 	; This processure will be called to map
  3092                              <1> 	; user's (ring 3) page tables to access phsical
  3093                              <1> 	; (flat/linear) memory addresses, directly (without
  3094                              <1> 	;  kernel's data transfer functions).
  3095                              <1> 	; 
  3096                              <1> 	; Purpose: Video memory access and shared memory access.
  3097                              <1> 	;
  3098                              <1> 	; INPUT -> 
  3099                              <1> 	;	EAX = Beginning address (physical).
  3100                              <1> 	;	EBX = User's buffer address ; 12/05/2017
  3101                              <1> 	;	ECX = Number of contiguous pages to be mapped.
  3102                              <1> 	; OUTPUT ->
  3103                              <1> 	;	User's page directory and pages tables
  3104                              <1> 	;	will be updated.
  3105                              <1> 	;	
  3106                              <1> 	;	If an old page table entry has valid page address, 
  3107                              <1> 	;	that page will be deallocated just before PTE will
  3108                              <1> 	;	be changed for direct (1 to 1) memory page access.
  3109                              <1> 	;
  3110                              <1> 	;	If old PTE value points to a swapped page,
  3111                              <1>         ;       that page (block) will be unlinked on swap disk. 
  3112                              <1> 	;
  3113                              <1> 	;	Newly allocated pages (except page tables) will not
  3114                              <1> 	;	be applied to Memory Allocation Table.
  3115                              <1> 	;	AVL bit 1 (PTE bit 10) of page table entry will be
  3116                              <1> 	;	used to indicate shared (direct) memory page; then,
  3117                              <1> 	;	this page will not be deallocated later during
  3118                              <1> 	;	process termination. (Memory Allocation Table and
  3119                              <1> 	;	free memory count will not be affected.
  3120                              <1> 	;	(Except deallocating page table's itself.)
  3121                              <1> 	;	
  3122                              <1> 	;      CF = 1 -> error (EAX = error code)
  3123                              <1> 	;      CF = 0 -> success (EAX = beginning address)
  3124                              <1> 	;
  3125                              <1> 	;; (Modified Registers -> none)
  3126                              <1> 	; Modified registers: ebp, edx, ecx, ebx, esi, edi	
  3127                              <1> 	;
  3128                              <1> 
  3129                              <1> 	;push	ebp
  3130                              <1> 	;push	ebx
  3131                              <1> 	;push	ecx
  3132                              <1> 	;push	edx
  3133 00005E0C 662500F0            <1> 	and	ax, PTE_A_CLEAR ; clear page offset
  3134 00005E10 50                  <1> 	push	eax
  3135                              <1> 	;and	ecx, ecx ; page count
  3136                              <1> 	;jz	dmem_acc_7  ; 'insufficient memory' error
  3137 00005E11 89C5                <1> 	mov	ebp, eax
  3138 00005E13 81C300004000        <1> 	add	ebx, CORE ; 12/05/2017
  3139                              <1> dmem_acc_0: 
  3140 00005E19 891D[3C750100]      <1> 	mov	[base_addr], ebx ; 12/05/2017
  3141 00005E1F A1[B8030300]        <1> 	mov	eax, [u.pgdir] ; page dir address (physical)
  3142 00005E24 E8D7F5FFFF          <1> 	call	get_pte
  3143                              <1> 		; EDX = Page table entry address (if CF=0)
  3144                              <1> 	        ;       Page directory entry address (if CF=1)
  3145                              <1> 		;       (Bit 0 value is 0 if PT is not present)
  3146                              <1> 		; EAX = Page table entry value (page address)
  3147                              <1> 		;	CF = 1 -> PDE not present or invalid ? 	
  3148 00005E29 7324                <1> 	jnc	short dmem_acc_1
  3149                              <1> 	;
  3150 00005E2B E8B5F4FFFF          <1> 	call	allocate_page
  3151 00005E30 0F82AB000000        <1>         jc      dmem_acc_7  ; 'insufficient memory' error
  3152                              <1> 	;
  3153 00005E36 E824F5FFFF          <1> 	call 	clear_page
  3154                              <1> 	; EAX = Physical (base) address of the allocated (new) page
  3155 00005E3B 0C07                <1> 	or	al, PDE_A_PRESENT + PDE_A_WRITE + PDE_A_USER ; 4+2+1 = 7
  3156                              <1> 			   ; lower 3 bits are used as U/S, R/W, P flags
  3157                              <1> 			   ; (user, writable, present page)	
  3158 00005E3D 8902                <1> 	mov	[edx], eax ; Let's put the new page directory entry here !
  3159 00005E3F A1[B8030300]        <1> 	mov	eax, [u.pgdir]	
  3160 00005E44 E8B7F5FFFF          <1> 	call	get_pte
  3161 00005E49 0F8292000000        <1>         jc      dmem_acc_7 ; 'insufficient memory' error
  3162                              <1> dmem_acc_1:
  3163                              <1> 	; EAX = PTE value, EDX = PTE address
  3164 00005E4F A801                <1> 	test 	al, PTE_A_PRESENT
  3165 00005E51 750D                <1> 	jnz	short dmem_acc_2
  3166 00005E53 09C0                <1> 	or	eax, eax
  3167 00005E55 7468                <1> 	jz	short dmem_acc_6   ; Change PTE
  3168 00005E57 D1E8                <1> 	shr	eax, 1		; swap disk block (8 sectors) address
  3169                              <1> 	; unlink swap disk block
  3170 00005E59 E80CFBFFFF          <1> 	call	unlink_swap_block
  3171 00005E5E EB5F                <1> 	jmp	short dmem_acc_6
  3172                              <1> 
  3173                              <1> dmem_acc_2:
  3174 00005E60 A802                <1> 	test	al, PTE_A_WRITE   ; bit 1, writable (r/w) flag
  3175                              <1> 				  ; (must be 1)
  3176 00005E62 7550                <1> 	jnz	short dmem_acc_4
  3177                              <1> 	; Read only -duplicated- page (belongs to a parent or a child)
  3178 00005E64 66A90002            <1>         test    ax, PTE_DUPLICATED ; Was this page duplicated 
  3179                              <1> 				   ; as child's page ?
  3180 00005E68 7455                <1> 	jz	short dmem_acc_5 ; Change PTE but don't deallocate the page!
  3181                              <1> 
  3182                              <1> 	;push	edi
  3183                              <1> 	;push	esi
  3184                              <1> 
  3185 00005E6A 51                  <1> 	push	ecx
  3186                              <1> 	;push	ebx
  3187 00005E6B 8B1D[BC030300]      <1> 	mov	ebx, [u.ppgdir] ; parent's page dir address (physical)
  3188                              <1> 	
  3189                              <1> 	; check the parent's PTE value is read only & same page or not.. 
  3190 00005E71 89EF                <1> 	mov	edi, ebp
  3191 00005E73 C1EF16              <1> 	shr	edi, PAGE_D_SHIFT ; 22
  3192                              <1> 	; EDI = page directory entry index (0-1023)
  3193 00005E76 89EE                <1> 	mov	esi, ebp
  3194 00005E78 C1EE0C              <1> 	shr	esi, PAGE_SHIFT ; 12	
  3195 00005E7B 81E6FF030000        <1> 	and	esi, PTE_MASK
  3196                              <1> 	; ESI = page table entry index (0-1023)
  3197                              <1> 
  3198 00005E81 66C1E702            <1> 	shl	di, 2 ; * 4
  3199 00005E85 01FB                <1> 	add	ebx, edi ; PDE offset (for the parent)
  3200 00005E87 8B0F                <1> 	mov	ecx, [edi]
  3201 00005E89 F6C101              <1> 	test	cl, PDE_A_PRESENT ; present (valid) or not ?
  3202 00005E8C 7425                <1> 	jz	short dmem_acc_3	; parent process does not use this page
  3203 00005E8E 6681E100F0          <1> 	and	cx, PDE_A_CLEAR ; 0F000h ; Clear attribute bits
  3204 00005E93 66C1E602            <1> 	shl	si, 2 ; *4 
  3205 00005E97 01CE                <1> 	add	esi, ecx ; PTE offset (for the parent)
  3206 00005E99 8B1E                <1> 	mov	ebx, [esi]
  3207 00005E9B F6C301              <1> 	test	bl, PTE_A_PRESENT ; present or not ?
  3208 00005E9E 7413                <1> 	jz	short dmem_acc_3	; parent process does not use this page
  3209 00005EA0 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; Clear attribute bits 
  3210 00005EA4 6681E300F0          <1> 	and	bx, PTE_A_CLEAR ; 0F000h ; Clear attribute bits
  3211 00005EA9 39D8                <1> 	cmp	eax, ebx	; parent's and child's pages are same ?
  3212 00005EAB 7506                <1> 	jne	short dmem_acc_3	; not same page
  3213                              <1> 				; deallocate the child's page
  3214 00005EAD 800E02              <1>         or      byte [esi], PTE_A_WRITE ; convert to writable page (parent)
  3215                              <1> 	;pop	ebx
  3216 00005EB0 59                  <1> 	pop	ecx
  3217 00005EB1 EB0C                <1> 	jmp	short dmem_acc_5
  3218                              <1> dmem_acc_3:
  3219                              <1> 	;pop	ebx
  3220 00005EB3 59                  <1> 	pop	ecx
  3221                              <1> dmem_acc_4:	
  3222 00005EB4 66A90004            <1> 	test	ax, PTE_SHARED ; shared or direct memory access indicator
  3223 00005EB8 7505                <1> 	jnz	short dmem_acc_5   ; AVL bit 1 = 1, do not deallocate this page!
  3224                              <1> 	;
  3225                              <1> 	;and	ax, PTE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
  3226 00005EBA E804F6FFFF          <1> 	call	deallocate_page
  3227                              <1> dmem_acc_5:
  3228                              <1> 	;pop	esi
  3229                              <1> 	;pop	edi
  3230                              <1> dmem_acc_6:
  3231 00005EBF 89E8                <1> 	mov	eax, ebp ; physical page (offset=0) address
  3232                              <1> 	; EAX = memory page address
  3233                              <1> 	; EDX = PTE entry address (physical)
  3234 00005EC1 660D0704            <1> 	or	ax, PTE_A_PRESENT+PTE_A_USER+PTE_A_WRITE+PTE_SHARED
  3235                              <1> 			; present flag, bit 0 = 1
  3236                              <1> 			; user flag, bit 2 = 1	
  3237                              <1> 			; writable flag, bit 1 = 1
  3238                              <1> 			; direct memory access flag, bit 10 = 1
  3239                              <1> 			; (This page must not be deallocated!)
  3240 00005EC5 8902                <1> 	mov	[edx], eax  ; Update PTE value
  3241 00005EC7 49                  <1> 	dec	ecx ; remain count of contiguous pages
  3242 00005EC8 741E                <1> 	jz	short dmem_acc_8
  3243 00005ECA 81C500100000        <1> 	add	ebp, PAGE_SIZE ; next physical page address
  3244                              <1> 	; 22/07/2017
  3245                              <1> 	;mov	eax, ebp
  3246                              <1> 	; 12/05/2017
  3247 00005ED0 8B1D[3C750100]      <1> 	mov	ebx, [base_addr] ; linear address (virtual+CORE)
  3248 00005ED6 81C300100000        <1> 	add	ebx, PAGE_SIZE	; next linear address
  3249 00005EDC E938FFFFFF          <1>         jmp     dmem_acc_0
  3250                              <1> dmem_acc_7:  ; ERROR ! 
  3251 00005EE1 C7042404000000      <1> 	mov	dword [esp], ERR_MINOR_IM 
  3252                              <1> 		; Insufficient memory (minor) error!
  3253                              <1> 		; Major error = 0 (No protection fault)	
  3254                              <1> 	; cf = 1
  3255                              <1> dmem_acc_8:
  3256 00005EE8 58                  <1> 	pop	eax
  3257                              <1> 	;pop	edx
  3258                              <1> 	;pop	ecx
  3259                              <1> 	;pop	ebx
  3260                              <1> 	;pop	ebp
  3261 00005EE9 C3                  <1> 	retn
  3262                              <1> 
  3263                              <1> deallocate_user_pages:
  3264                              <1> 	; 20/05/2017
  3265                              <1> 	; 15/05/2017
  3266                              <1> 	; 20/02/2017
  3267                              <1> 	; 19/02/2017 (TRDOS 386 = TRDOS v2.0)
  3268                              <1> 	;
  3269                              <1> 	; Deallocate virtually contiguous user pages (memory block)
  3270                              <1> 	; (caller: 'sysdalloc' system call)
  3271                              <1> 	;
  3272                              <1> 	; INPUT ->
  3273                              <1> 	;	EBX = VIRTUAL ADDRESS (beginning address)
  3274                              <1> 	;	ECX = byte count
  3275                              <1> 	;	[u.pgdir] = user's page directory
  3276                              <1> 	;	[u.ppdir] = parent's page directory
  3277                              <1> 	;
  3278                              <1> 	; OUTPUT ->
  3279                              <1> 	;    If CF = 0 	
  3280                              <1> 	;	EAX = Deallocated memory bytes
  3281                              <1> 	;	  (Even if shared or read only pages will not be
  3282                              <1> 	;	   deallocated on M.A.T., this byte count will be
  3283                              <1> 	;	   returned as virtually deallocated bytes; in fact
  3284                              <1> 	;	   virtually deallocated user pages * 4096.) 
  3285                              <1> 	;	EBX = Virtual address (as rounded up)
  3286                              <1> 	;    If CF = 1    	
  3287                              <1> 	;	EAX = 0 (there is not any deallocated pages)
  3288                              <1> 	;
  3289                              <1> 	; Note: Empty page tables will not be deallocated!!!
  3290                              <1> 	;     (they will be deallocated at process termination stage)
  3291                              <1> 	;
  3292                              <1> 	; Modified Registers -> EAX, EDX, ESI, EDI, EBX, ECX, EBP
  3293                              <1> 	;
  3294 00005EEA 89DE                <1> 	mov	esi, ebx
  3295 00005EEC 89F7                <1> 	mov	edi, esi
  3296 00005EEE 01CF                <1> 	add	edi, ecx
  3297 00005EF0 81C6FF0F0000        <1> 	add	esi, PAGE_SIZE - 1  ; 4095 (round up)	
  3298 00005EF6 C1EE0C              <1> 	shr	esi, PAGE_SHIFT
  3299 00005EF9 C1EF0C              <1> 	shr	edi, PAGE_SHIFT
  3300 00005EFC 89F8                <1> 	mov	eax, edi ; end page
  3301 00005EFE 29F0                <1> 	sub	eax, esi ; end page - start page
  3302 00005F00 0F86D5000000        <1> 	jna	da_u_pd_err  ; < 1
  3303 00005F06 89F3                <1> 	mov	ebx, esi
  3304 00005F08 C1E30C              <1> 	shl	ebx, PAGE_SHIFT ; virtual address (as rounded up)
  3305 00005F0B 53                  <1> 	push	ebx ; *
  3306 00005F0C 89C1                <1> 	mov	ecx, eax ; page count
  3307 00005F0E C1E00C              <1> 	shl	eax, PAGE_SHIFT ; byte count as adjusted
  3308 00005F11 50                  <1> 	push	eax ; **
  3309 00005F12 8B1D[B8030300]      <1> 	mov	ebx, [u.pgdir] ; physical addr of user's page dir
  3310 00005F18 81C600040000        <1>  	add	esi, CORE/PAGE_SIZE 
  3311 00005F1E 89F7                <1> 	mov	edi, esi
  3312 00005F20 81E7FF030000        <1> 	and	edi, PTE_MASK ; PTE entry in the page table
  3313 00005F26 57                  <1> 	push	edi ; *** ; PTE index (of page directory)
  3314 00005F27 C1EE0A              <1> 	shr	esi, PAGE_D_SHIFT - PAGE_SHIFT ; 22-12=10
  3315 00005F2A 89F2                <1> 	mov	edx, esi 
  3316                              <1> 	; EDX = PDE index
  3317 00005F2C C1E602              <1> 	shl	esi, 2 ; convert PDE index to dword offset
  3318 00005F2F 01DE                <1> 	add	esi, ebx ; add page directory address
  3319                              <1> da_u_pd_1:
  3320 00005F31 AD                  <1> 	lodsd
  3321                              <1> 	;
  3322 00005F32 89F5                <1> 	mov	ebp, esi ; 20/02/2017
  3323                              <1> 	; EBP = next PDE address
  3324                              <1> 	;
  3325 00005F34 A801                <1> 	test	al, PDE_A_PRESENT ; bit 0, present flag (must be 1)
  3326 00005F36 0F8494000000        <1> 	jz	da_u_pd_3 ; 20/05/2017	
  3327 00005F3C 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
  3328                              <1> 	; EAX = PHYSICAL (flat) ADDRESS OF THE PAGE TABLE
  3329 00005F40 8B3C24              <1> 	mov	edi, [esp] ; ***
  3330                              <1> 	; EDI = PTE index (of complete page directory)
  3331                              <1> 	;and	edi, PTE_MASK ; PTE entry in the page table
  3332 00005F43 C1E702              <1> 	shl	edi, 2 ; convert PTE index to dword offset
  3333 00005F46 89FE                <1> 	mov	esi, edi ; PTE offset in page table (0-4092)
  3334 00005F48 01C6                <1> 	add	esi, eax ; now, esi points to requested PTE
  3335                              <1> da_u_pt_0:
  3336 00005F4A AD                  <1> 	lodsd
  3337 00005F4B A801                <1> 	test	al, PTE_A_PRESENT ; bit 0, present flag (must be 1)
  3338 00005F4D 743F                <1> 	jz	short da_u_pt_1
  3339                              <1> 	;
  3340 00005F4F A802                <1> 	test	al, PTE_A_WRITE   ; bit 1, writable (r/w) flag
  3341                              <1> 				  ; (must be 1)
  3342 00005F51 7549                <1> 	jnz	short da_u_pt_3
  3343                              <1> 	; Read only -duplicated- page (belongs to a parent or a child)
  3344 00005F53 66A90002            <1>         test    ax, PTE_DUPLICATED ; Was this page duplicated 
  3345                              <1> 				   ; as child's page ?
  3346 00005F57 744E                <1> 	jz	short da_u_pt_4 ; Clear PTE but don't deallocate the page!
  3347                              <1> 	;
  3348                              <1> 	; check the parent's PTE value is read only & same page or not.. 
  3349                              <1> 	; EDX = page directory entry index (0-1023)
  3350 00005F59 52                  <1> 	push	edx ; ****
  3351                              <1> 	; EDI = page table entry offset (0-4092)
  3352 00005F5A 8B1D[BC030300]      <1> 	mov	ebx, [u.ppgdir] ; page directory of the parent process
  3353 00005F60 66C1E202            <1> 	shl	dx, 2 ; *4 
  3354 00005F64 01D3                <1> 	add	ebx, edx ; PDE address (for the parent)
  3355 00005F66 8B13                <1> 	mov	edx, [ebx] ; page table address
  3356 00005F68 F6C201              <1> 	test	dl, PDE_A_PRESENT ; present (valid) or not ?
  3357 00005F6B 742E                <1> 	jz	short da_u_pt_2	; parent process does not use this page
  3358 00005F6D 6681E200F0          <1> 	and	dx, PDE_A_CLEAR ; 0F000h ; Clear attribute bits
  3359                              <1> 	; EDI = page table entry offset (0-4092)
  3360 00005F72 01D7                <1> 	add	edi, edx	; PTE address (for the parent)
  3361 00005F74 8B1F                <1> 	mov	ebx, [edi]
  3362 00005F76 F6C301              <1> 	test	bl, PTE_A_PRESENT ; present or not ?
  3363 00005F79 7420                <1> 	jz	short da_u_pt_2	; parent process does not use this page
  3364 00005F7B 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; Clear attribute bits 
  3365 00005F7F 6681E300F0          <1> 	and	bx, PTE_A_CLEAR ; 0F000h ; Clear attribute bits
  3366 00005F84 39D8                <1> 	cmp	eax, ebx	; parent's and child's pages are same ?
  3367 00005F86 7513                <1> 	jne	short da_u_pt_2	; not same page
  3368                              <1> 				; deallocate the child's page
  3369 00005F88 800F02              <1>         or      byte [edi], PTE_A_WRITE ; convert to writable page (parent)
  3370 00005F8B 5A                  <1> 	pop	edx ; ****
  3371 00005F8C EB19                <1> 	jmp	short da_u_pt_4
  3372                              <1> da_u_pt_1:
  3373 00005F8E 09C0                <1> 	or	eax, eax	; swapped page ?
  3374 00005F90 741C                <1> 	jz	short da_u_pt_5	; no
  3375                              <1> 				; yes
  3376 00005F92 D1E8                <1> 	shr	eax, 1
  3377 00005F94 E8D1F9FFFF          <1> 	call	unlink_swap_block ; Deallocate swapped page block
  3378                              <1> 				  ; on the swap disk (or in file)
  3379 00005F99 EB13                <1> 	jmp	short da_u_pt_5
  3380                              <1> da_u_pt_2:
  3381 00005F9B 5A                  <1> 	pop	edx ; ****
  3382                              <1> da_u_pt_3:
  3383 00005F9C 66A90004            <1> 	test	ax, PTE_SHARED	; shared or direct memory access indicator
  3384 00005FA0 7505                <1> 	jnz	short da_u_pt_4	; AVL bit 1 = 1, do not deallocate this page!
  3385                              <1> 	;
  3386                              <1> 	;and	ax, PTE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
  3387 00005FA2 E81CF5FFFF          <1> 	call	deallocate_page ; set the mem allocation bit of this page
  3388                              <1> da_u_pt_4:
  3389 00005FA7 C746FC00000000      <1> 	mov	dword [esi-4], 0 ; clear/reset PTE (child, dupl. as parent)
  3390                              <1> da_u_pt_5:
  3391                              <1> 	; 20/05/2017
  3392 00005FAE 58                  <1> 	pop	eax ; *** PTE index (of page directory)
  3393 00005FAF 49                  <1> 	dec	ecx ; remain page count
  3394 00005FB0 7426                <1> 	jz	short da_u_pd_4
  3395 00005FB2 40                  <1> 	inc	eax ; next PTE
  3396 00005FB3 6625FF03            <1> 	and	ax, PTE_MASK ; PTE entry index in the page table
  3397 00005FB7 50                  <1> 	push	eax ; *** (save again)
  3398                              <1> 	;mov	edi, eax
  3399                              <1> 	;and 	di, PTE_MASK
  3400                              <1> 	;cmp	edi, PAGE_SIZE / 4 ; 1024
  3401                              <1> 	;jnb	short da_u_pd_2
  3402 00005FB8 89C7                <1> 	mov	edi, eax
  3403 00005FBA C1E702              <1> 	shl	edi, 2 ; convert index to dword offset
  3404                              <1> 	;test	ax, PTE_MASK ; 3FFh
  3405 00005FBD 09C0                <1> 	or	eax, eax
  3406 00005FBF 7589                <1> 	jnz	short da_u_pt_0 ; 1-1023
  3407                              <1> da_u_pd_2:
  3408 00005FC1 42                  <1> 	inc	edx
  3409                              <1> 	; 20/05/2017
  3410 00005FC2 6681E2FF03          <1> 	and	dx, PTE_MASK  ; 3FFh
  3411 00005FC7 740F                <1> 	jz	short da_u_pd_4  ; 0 (1024)
  3412                              <1> 	;cmp	edx, 1024
  3413                              <1> 	;jnb	short da_u_pd_4
  3414 00005FC9 89EE                <1> 	mov	esi, ebp ; 20/02/2017
  3415 00005FCB E961FFFFFF          <1> 	jmp	da_u_pd_1
  3416                              <1> da_u_pd_3:
  3417                              <1> 	; 15/05/2017 (empty page directory entry)
  3418 00005FD0 81E900040000        <1> 	sub	ecx, 1024
  3419 00005FD6 77E9                <1> 	ja	short da_u_pd_2 ; 20/05/2017
  3420                              <1> da_u_pd_4:
  3421 00005FD8 58                  <1> 	pop	eax ; **
  3422 00005FD9 5B                  <1> 	pop	ebx ; *
  3423 00005FDA C3                  <1> 	retn
  3424                              <1> 
  3425                              <1> da_u_pd_err:
  3426 00005FDB 31C0                <1> 	xor	eax, eax
  3427 00005FDD F9                  <1> 	stc	
  3428 00005FDE C3                  <1> 	retn
  3429                              <1> 
  3430                              <1> allocate_user_pages:
  3431                              <1> 	; 20/05/2017
  3432                              <1> 	; 01/05/2017, 02/05/2017, 15/05/2017
  3433                              <1> 	; 04/03/2017
  3434                              <1> 	; 20/02/2017 (TRDOS 386 = TRDOS v2.0)
  3435                              <1> 	;
  3436                              <1> 	; Allocate physically contiguous user pages (memory block)
  3437                              <1> 	; (caller: 'sysalloc' system call)
  3438                              <1> 	;
  3439                              <1> 	; Note: This procedure does not alloc a page's itself
  3440                              <1> 	;	(page bit) on Memory Allocation Table.
  3441                              <1> 	;	(allocate_memory_block is needed before this proc)
  3442                              <1> 	;
  3443                              <1> 	; INPUT ->
  3444                              <1> 	;	EAX = PHYSICAL ADDRESS (beginning address)
  3445                              <1> 	;	EBX = VIRTUAL ADDRESS (beginning address)
  3446                              <1> 	;	ECX = byte count (>=4096)
  3447                              <1> 	;	[u.pgdir] = user's page directory
  3448                              <1> 	;	
  3449                              <1> 	;	Note: All addresses are (must be) already adjusted
  3450                              <1> 	;	to page	borders, otherwise, lower 12bits of addresses
  3451                              <1> 	;	and byte count would be truncated.
  3452                              <1> 	;
  3453                              <1> 	; OUTPUT ->
  3454                              <1> 	;	none
  3455                              <1> 	;
  3456                              <1> 	;	CF = 1 -> insufficient memory error
  3457                              <1> 	;
  3458                              <1> 	; Note: All pages will be allocated in physical page order 
  3459                              <1> 	;	from the beginning page address. 
  3460                              <1> 	;	* A new page table will be added to the page dir
  3461                              <1> 	;	  when the requested PDE is invalid.
  3462                              <1> 	;	* Those pages will not be added to swap queue
  3463                              <1> 	;	  because main purpose of this allocation is to
  3464                              <1> 	;	  set a direct memory access (DMA controller) buffer.
  3465                              <1> 	;	 (Swapping out a page in a DMA buffer would be wrong!)
  3466                              <1> 	;	* Previous content of page tables (PTEs) would be
  3467                              <1> 	;	  (should be) deallocated before entering this
  3468                              <1> 	;	  procedure. So, new page table entries (PTEs)
  3469                              <1> 	;	  directly will be written without checking
  3470                              <1> 	;	  their previous content.	
  3471                              <1> 	;	* Only solution to increase free memory by removing
  3472                              <1> 	;	  that non-swappable memory block is to terminate
  3473                              <1> 	;	  the process or to wait until the process will 
  3474                              <1> 	;	  deallocate that memory block as itself. ('sysdalloc')
  3475                              <1> 	;	  (No problem, if the process does not grab all of
  3476                              <1> 	;	  -very big amount of- free memory by using
  3477                              <1> 	;	  'sysalloc' system call!?)
  3478                              <1> 	;	  (Even if the process has grabbed all of free memory, 
  3479                              <1> 	;	  no problem if the process is not running in 
  3480                              <1> 	;	  multitasking mode. No problem in multitasking
  3481                              <1> 	;	  mode if there is not another process which is running
  3482                              <1> 	;	  or waiting or sleeping for an event as it's pages
  3483                              <1> 	;	  are swapped-out. But a new process can not start to
  3484                              <1> 	;	  run if all of free memory has beeen allocated 
  3485                              <1> 	;	  by running processes. Deallocation -'sysdalloc'- 
  3486                              <1> 	;	  or terminate a running process is needed 
  3487                              <1> 	;	  in order to run a new process.) 
  3488                              <1> 	;
  3489                              <1> 	; Modified Registers -> EAX, EDX, ESI, EDI, EBX, ECX, EBP
  3490                              <1> 	;
  3491                              <1> 
  3492                              <1> 	; 01/05/2017
  3493 00005FDF 662500F0            <1> 	and	ax, ~PAGE_OFF
  3494 00005FE3 6681E300F0          <1> 	and	bx, ~PAGE_OFF
  3495                              <1> 	; 02/05/2017 
  3496 00005FE8 BD00F0FFFF          <1> 	mov	ebp, 0FFFFF000h ; 4 Giga Bytes - 4096 Bytes (for Stack)
  3497 00005FED C1E90C              <1> 	shr	ecx, PAGE_SHIFT ; page count
  3498 00005FF0 83F901              <1> 	cmp	ecx, 1
  3499 00005FF3 7251                <1> 	jb	short a_u_im_retn
  3500 00005FF5 89C2                <1> 	mov	edx, eax
  3501 00005FF7 01CA                <1> 	add	edx, ecx
  3502 00005FF9 724B                <1> 	jc	short a_u_im_retn
  3503 00005FFB 39D5                <1> 	cmp	ebp, edx
  3504 00005FFD 7247                <1> 	jb	short a_u_im_retn
  3505 00005FFF 89DA                <1> 	mov	edx, ebx
  3506 00006001 81C200004000        <1> 	add	edx, CORE
  3507 00006007 723D                <1> 	jc	short a_u_im_retn	
  3508 00006009 01CA                <1> 	add	edx, ecx
  3509 0000600B 7239                <1> 	jc	short a_u_im_retn
  3510 0000600D 39D5                <1> 	cmp	ebp, edx
  3511 0000600F 7235                <1> 	jb	short a_u_im_retn
  3512                              <1> 	;
  3513 00006011 89C5                <1> 	mov	ebp, eax ; physical address
  3514 00006013 89DE                <1> 	mov	esi, ebx
  3515 00006015 81C600004000        <1> 	add	esi, CORE ; start of user's memory (4M) 
  3516 0000601B C1EE0C              <1> 	shr	esi, PAGE_SHIFT ; higher 20 bits of the linear address
  3517                              <1> 	;shr	ecx, PAGE_SHIFT ; page count
  3518 0000601E 8B1D[B8030300]      <1> 	mov	ebx, [u.pgdir] ; physical addr of user's page dir
  3519 00006024 89F7                <1> 	mov	edi, esi
  3520 00006026 81E7FF030000        <1> 	and	edi, PTE_MASK ; PTE entry index in the page table
  3521 0000602C 57                  <1> 	push	edi  ; * ; PTE index (in page directory)
  3522 0000602D C1EE0A              <1> 	shr	esi, PAGE_D_SHIFT - PAGE_SHIFT ; 22-12=10
  3523 00006030 89F2                <1> 	mov	edx, esi 
  3524                              <1> 	; EDX = PDE index
  3525 00006032 C1E602              <1> 	shl	esi, 2 ; convert PDE index to dword offset
  3526 00006035 01DE                <1> 	add	esi, ebx ; add page directory address
  3527                              <1> a_u_pd_0:
  3528 00006037 AD                  <1> 	lodsd
  3529                              <1> 	;
  3530 00006038 89F3                <1> 	mov	ebx, esi ; next PDE address
  3531                              <1> 	;
  3532 0000603A A801                <1> 	test	al, PDE_A_PRESENT ; bit 0, present flag (must be 1)
  3533 0000603C 7513                <1> 	jnz	short a_u_pd_2
  3534                              <1> 	;
  3535                              <1> 	; empty PDE (it does not point to valid page table address)
  3536 0000603E E8A2F2FFFF          <1> 	call	allocate_page  ; (allocate a new page table)
  3537 00006043 7302                <1> 	jnc	short a_u_pd_1 ; OK... now, we have a new page table.
  3538                              <1> 	; cf = 1
  3539                              <1> 	; There is not a free memory page to allocate a new page table !!!
  3540 00006045 5E                  <1> 	pop	esi ; *
  3541                              <1> a_u_im_retn:
  3542 00006046 C3                  <1> 	retn	; return to 'sysalloc' with 'insufficient memory' error
  3543                              <1> 	;
  3544                              <1> a_u_pd_1: ; clear the new page table content 
  3545                              <1> 	; EAX = Physical (base) address of the new page table
  3546 00006047 E813F3FFFF          <1> 	call	clear_page ; Clear page content
  3547                              <1> 	;
  3548 0000604C 0C07                <1> 	or	al, PDE_A_PRESENT + PDE_A_WRITE + PDE_A_USER
  3549                              <1> 		 ; set bit 0, bit 1 and bit 2 to 1
  3550                              <1> 		 ; (present, writable, user)
  3551 0000604E 8946FC              <1> 	mov	[esi-4], eax
  3552                              <1> a_u_pd_2:
  3553 00006051 662500F0            <1> 	and	ax, PDE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
  3554                              <1> 	; EAX = PHYSICAL (flat) ADDRESS OF THE PAGE TABLE
  3555 00006055 8B3C24              <1> 	mov	edi, [esp] ; *
  3556                              <1> 	; EDI = PTE index (of page directory)
  3557                              <1> 	;and	edi, PTE_MASK ; PTE entry index in the page table	
  3558                              <1> 	; EBX = next PDE address
  3559 00006058 89FE                <1> 	mov	esi, edi ; PTE index in page table (0-1023)
  3560 0000605A C1E702              <1> 	shl	edi, 2 ; convert PTE index to dword offset
  3561 0000605D 01C7                <1> 	add	edi, eax ; now, edi points to requested PTE
  3562                              <1> a_u_pt_0:
  3563                              <1> 	; 02/05/2017
  3564 0000605F 8B07                <1> 	mov	eax, [edi]
  3565                              <1> 	;
  3566 00006061 A801                <1> 	test	al, PTE_A_PRESENT ; bit 0, present flag (must be 1)
  3567 00006063 7445                <1> 	jz	short a_u_pt_1
  3568                              <1> 	;
  3569 00006065 A802                <1> 	test	al, PTE_A_WRITE   ; bit 1, writable (r/w) flag
  3570                              <1> 				  ; (must be 1)
  3571 00006067 7550                <1> 	jnz	short a_u_pt_3
  3572                              <1> 	; Read only -duplicated- page (belongs to a parent or a child)
  3573 00006069 66A90002            <1>         test    ax, PTE_DUPLICATED ; Was this page duplicated 
  3574                              <1> 				   ; as child's page ?
  3575 0000606D 7455                <1> 	jz	short a_u_pt_4	; Clear PTE but don't deallocate the page!
  3576                              <1> 	;
  3577                              <1> 	; check the parent's PTE value is read only & same page or not.. 
  3578                              <1> 	; EDX = page directory entry index (0-1023)
  3579 0000606F 52                  <1> 	push	edx ; **
  3580 00006070 53                  <1> 	push	ebx ; ***
  3581                              <1> 	; ESI = page table entry index (0-1023)
  3582                              <1> 	;push	esi ; **** ; 20/05/2017
  3583 00006071 8B1D[BC030300]      <1> 	mov	ebx, [u.ppgdir] ; page directory of the parent process
  3584 00006077 66C1E202            <1> 	shl	dx, 2 ; *4 
  3585 0000607B 01D3                <1> 	add	ebx, edx ; PTE address,0 (for the parent)
  3586 0000607D 8B13                <1> 	mov	edx, [ebx] ; page table address
  3587 0000607F F6C201              <1> 	test	dl, PDE_A_PRESENT ; present (valid) or not ?
  3588 00006082 7433                <1> 	jz	short a_u_pt_2	; parent process does not use this page
  3589 00006084 6681E200F0          <1> 	and	dx, PDE_A_CLEAR ; 0F000h ; Clear attribute bits
  3590 00006089 66C1E602            <1> 	shl	si, 2 ; *4
  3591                              <1> 	; ESI = page table entry offset (0-4092)
  3592 0000608D 01D6                <1> 	add	esi, edx	; PTE address (for the parent)
  3593 0000608F 8B1E                <1> 	mov	ebx, [esi]
  3594 00006091 F6C301              <1> 	test	bl, PTE_A_PRESENT ; present or not ?
  3595 00006094 7421                <1> 	jz	short a_u_pt_2	; parent process does not use this page
  3596 00006096 662500F0            <1> 	and	ax, PTE_A_CLEAR ; 0F000h ; Clear attribute bits 
  3597 0000609A 6681E300F0          <1> 	and	bx, PTE_A_CLEAR ; 0F000h ; Clear attribute bits
  3598 0000609F 39D8                <1> 	cmp	eax, ebx	; parent's and child's pages are same ?
  3599 000060A1 7514                <1> 	jne	short a_u_pt_2	; not same page
  3600                              <1> 				; deallocate the child's page
  3601 000060A3 800E02              <1>         or      byte [esi], PTE_A_WRITE ; convert to writable page (parent)
  3602                              <1> 	;pop	esi ; **** ; 20/05/2017
  3603 000060A6 5B                  <1> 	pop	ebx ; ***
  3604 000060A7 5A                  <1> 	pop	edx ; **
  3605 000060A8 EB1A                <1> 	jmp	short a_u_pt_4
  3606                              <1> a_u_pt_1:
  3607 000060AA 09C0                <1> 	or	eax, eax	; swapped page ?
  3608 000060AC 7416                <1> 	jz	short a_u_pt_4	; no
  3609                              <1> 				; yes
  3610 000060AE D1E8                <1> 	shr	eax, 1
  3611 000060B0 E8B5F8FFFF          <1> 	call	unlink_swap_block ; Deallocate swapped page block
  3612                              <1> 				  ; on the swap disk (or in file)
  3613 000060B5 EB0D                <1> 	jmp	short a_u_pt_4
  3614                              <1> a_u_pt_2:
  3615                              <1> 	;pop	esi ; **** ; 20/05/2017
  3616 000060B7 5B                  <1> 	pop	ebx ; ***
  3617 000060B8 5A                  <1> 	pop	edx ; **
  3618                              <1> a_u_pt_3:
  3619 000060B9 66A90004            <1> 	test	ax, PTE_SHARED	; shared or direct memory access indicator
  3620 000060BD 7505                <1> 	jnz	short a_u_pt_4	; AVL bit 1 = 1, do not deallocate this page!
  3621                              <1> 	;
  3622                              <1> 	;and	ax, PTE_A_CLEAR ; 0F000h ; clear lower 12 (attribute) bits
  3623 000060BF E8FFF3FFFF          <1> 	call	deallocate_page ; set the mem allocation bit of this page
  3624                              <1> 	;
  3625                              <1> a_u_pt_4:
  3626 000060C4 89E8                <1> 	mov	eax, ebp ; physical address
  3627 000060C6 0C07                <1> 	or	al, PTE_A_PRESENT + PTE_A_WRITE + PTE_A_USER ; 04/03/2017
  3628 000060C8 AB                  <1> 	stosd
  3629 000060C9 5E                  <1> 	pop	esi ; * ; 20/05/2017
  3630 000060CA 49                  <1> 	dec	ecx ; remain page count
  3631 000060CB 7417                <1> 	jz	short a_u_pd_5
  3632 000060CD 81C500100000        <1> 	add	ebp, PAGE_SIZE
  3633 000060D3 46                  <1> 	inc	esi ; next PTE (index)
  3634                              <1> 	; 20/05/2017
  3635                              <1> 	;cmp	esi, PAGE_SIZE/4 ; 1024
  3636                              <1> 	;jb	short a_u_pt_0
  3637 000060D4 6681E6FF03          <1> 	and	si, PTE_MASK ; 3FFh (0 to 1023)
  3638 000060D9 56                  <1> 	push	esi ; *
  3639 000060DA 7583                <1> 	jnz	short a_u_pt_0 ; > 0 (<1024)
  3640                              <1> a_u_pd_3:
  3641 000060DC 42                  <1> 	inc	edx
  3642                              <1> ;	cmp	edx, 1024
  3643                              <1> ;	jnb	short a_u_pd_4 ; 02/05/2017 (error!, ecx > 0)
  3644 000060DD 89DE                <1> 	mov	esi, ebx ; the next PDE address
  3645 000060DF E953FFFFFF          <1> 	jmp	a_u_pd_0
  3646                              <1> a_u_pd_4:
  3647                              <1> 	; 02/05/2017
  3648                              <1> ;	stc
  3649                              <1> a_u_pd_5:
  3650                              <1> 	; 20/05/2017
  3651                              <1> 	;pop	edi ; *
  3652 000060E4 C3                  <1> 	retn
  3653                              <1> 
  3654                              <1> 
  3655                              <1> ; /// End Of MEMORY MANAGEMENT FUNCTIONS ///
  3656                              <1> 
  3657                              <1> ;; Data:
  3658                              <1> 
  3659                              <1> ; 09/03/2015
  3660                              <1> ;swpq_count: dw 0 ; count of pages on the swap que
  3661                              <1> ;swp_drv:    dd 0 ; logical drive description table address of the swap drive/disk
  3662                              <1> ;swpd_size:  dd 0 ; size of swap drive/disk (volume) in sectors (512 bytes). 		  				
  3663                              <1> ;swpd_free:  dd 0 ; free page blocks (4096 bytes) on swap disk/drive (logical)
  3664                              <1> ;swpd_next:  dd 0 ; next free page block
  3665                              <1> ;swpd_last:  dd 0 ; last swap page block
  2676                                  %include 'timer.s'   ; 17/01/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - timer.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 15/01/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 17/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ;
    15                              <1> ; Derived from 'IBM PC-AT' BIOS source code (1985) 
    16                              <1> ; ****************************************************************************
    17                              <1> 
    18                              <1> ; TRDOS 386  (TRDOS v2.0) Kernel - TIMER & REAL TIME CLOCK (BIOS) FUNCTIONS
    19                              <1> 
    20                              <1> ; IBM PC-AT BIOS Source Code ('BIOS2.ASM')
    21                              <1> ; TITLE BIOS2 ---- 06/10/85 BIOS INTERRUPT ROUTINES
    22                              <1> 
    23                              <1> ;
    24                              <1> ; ///////// TIMER (& REAL TIME CLOCK) FUNCTIONS ///////////////
    25                              <1> 
    26                              <1> int1Ah:
    27                              <1> 	; 29/01/2016
    28                              <1> 	; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
    29 000060E5 9C                  <1> 	pushfd
    30 000060E6 0E                  <1> 	push 	cs
    31 000060E7 E801000000          <1> 	call 	TIME_OF_DAY_1
    32 000060EC C3                  <1> 	retn
    33                              <1> 
    34                              <1> ;--- INT  1A H -- (TIME OF DAY) -------------------------------------------------
    35                              <1> ;       THIS BIOS ROUTINE ALLOWS THE CLOCKS TO BE SET OR READ			:
    36                              <1> ;										:
    37                              <1> ; PARAMETERS:									:
    38                              <1> ;     (AH) = 00H  READ THE CURRENT SETTING AND RETURN WITH,			:
    39                              <1> ;                      (CX) = HIGH PORTION OF COUNT				:
    40                              <1> ;                      (DX) = LOW PORTION OF COUNT				:
    41                              <1> ;                      (AL) = 0 TIMER HAS NOT PASSED 24 HOURS SINCE LAST READ	:
    42                              <1> ;                             1 IF ON ANOTHER DAY. (RESET TO ZERO AFTER READ)	:
    43                              <1> ;										:
    44                              <1> ;     (AH) = 01H  SET THE CURRENT CLOCK USING,					:
    45                              <1> ;		     (CX) = HIGH PORTION OF COUNT				:
    46                              <1> ;		     (DX) = LOW PORTION OF COUNT.				:
    47                              <1> ;										:
    48                              <1> ;               NOTE: COUNTS OCCUR AT THE RATE OF 1193180/65536 COUNTS/SECOND	:
    49                              <1> ;                            (OR ABOUT 18.2 PER SECOND -- SEE EQUATES)		:
    50                              <1> ;										:
    51                              <1> ;     (AH) = 02H  READ THE REAL TIME CLOCK AND RETURN WITH,			:
    52                              <1> ;                      (CH) = HOURS IN BCD (00-23)				:
    53                              <1> ;                      (CL) = MINUTES IN BCD (00-59)				:
    54                              <1> ;                      (DH) = SECONDS IN BCD (00-59)				:
    55                              <1> ;                      (DL) = DAYLIGHT SAVINGS ENABLE (00-01)			:
    56                              <1> ;										:
    57                              <1> ;     (AH) = 03H  SET THE REAL TIME CLOCK USING,				:
    58                              <1> ;                     (CH) = HOURS IN BCD (00-23)				:
    59                              <1> ;                     (CL) = MINUTES IN BCD (00-59)				:
    60                              <1> ;                     (DH) = SECONDS IN BCD (00-59)				:
    61                              <1> ;                     (DL) = 01 IF DAYLIGHT SAVINGS ENABLE OPTION, ELSE 00.	:
    62                              <1> ;										:
    63                              <1> ;             NOTE: (DL) = 00 IF DAYLIGHT SAVINGS TIME ENABLE IS NOT ENABLED.	:
    64                              <1> ;                   (DL) = 01 ENABLES TWO SPECIAL UPDATES THE LAST SUNDAY IN	:
    65                              <1> ;	           APRIL   (1:59:59 --> 3:00:00 AM) AND THE LAST SUNDAY IN	:
    66                              <1> ;                   OCTOBER (1:59:59 --> 1:00:00 AM) THE FIRST TIME.		:
    67                              <1> ;										:
    68                              <1> ;     (AH) = 04H  READ THE DATE FROM THE REAL TIME CLOCK AND RETURN WITH,	:
    69                              <1> ;                      (CH) = CENTURY IN BCD (19 OR 20)				:
    70                              <1> ;                      (CL) = YEAR IN BCD (00-99)				:
    71                              <1> ;                      (DH) = MONTH IN BCD (01-12)				:
    72                              <1> ;                      (DL) = DAY IN BCD (01-31).				:
    73                              <1> ;										:
    74                              <1> ;     (AH) = 05H  SET THE DATE INTO THE REAL TIME CLOCK USING,			:
    75                              <1> ;                     (CH) = CENTURY IN BCD (19 OR 20)				:
    76                              <1> ;                     (CL) = YEAR IN BCD (00-99)				:
    77                              <1> ;                     (DH) = MONTH IN BCD (01-12)				:
    78                              <1> ;                     (DL) = DAY IN BCD (01-31).				:
    79                              <1> ;										:
    80                              <1> ;     (AH) = 06H  SET THE ALARM TO INTERRUPT AT SPECIFIED TIME,			:
    81                              <1> ;                     (CH) = HOURS IN BCD (00-23 (OR FFH))			:
    82                              <1> ;                     (CL) = MINUTES IN BCD (00-59 (OR FFH))			:
    83                              <1> ;                     (DH) = SECONDS IN BCD (00-59 (OR FFH))			:
    84                              <1> ;										:
    85                              <1> ;     (AH) = 07H  RESET THE ALARM INTERRUPT FUNCTION.				:
    86                              <1> ;										:
    87                              <1> ; NOTES: FOR ALL RETURNS CY= 0 FOR SUCCESSFUL OPERATION.			:
    88                              <1> ;        FOR (AH)= 2, 4, 6 - CARRY FLAG SET IF REAL TIME CLOCK NOT OPERATING.	:
    89                              <1> ;        FOR (AH)= 6 - CARRY FLAG SET IF ALARM ALREADY ENABLED. 		:
    90                              <1> ;        FOR THE ALARM FUNCTION (AH = 6) THE USER MUST SUPPLY A ROUTINE AND	:
    91                              <1> ;         INTERCEPT THE CORRECT ADDRESS IN THE VECTOR TABLE FOR INTERRUPT 4AH.	:
    92                              <1> ;         USE 0FFH FOR ANY "DO NOT CARE" POSITION FOR INTERVAL INTERRUPTS.	:
    93                              <1> ;        INTERRUPTS ARE DISABLED DURING DATA MODIFICATION. 			:
    94                              <1> ;        AH & AL ARE RETURNED MODIFIED AND NOT DEFINED EXCEPT WHERE INDICATED.	:
    95                              <1> ;--------------------------------------------------------------------------------
    96                              <1> 
    97                              <1> ; 15/01/2017
    98                              <1> ; 14/01/2017
    99                              <1> ; 07/01/2017
   100                              <1> ; 02/01/2017
   101                              <1> ; 29/05/2016
   102                              <1> ; 29/01/2016
   103                              <1> ; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
   104                              <1> 
   105                              <1> ; 29/05/2016
   106                              <1> ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   107                              <1> int35h:  ; Date/Time functions
   108                              <1> 
   109                              <1> TIME_OF_DAY_1:
   110                              <1> 	;sti				; INTERRUPTS BACK ON
   111                              <1> 	; 29/05/2016
   112 000060ED 80642408FE          <1> 	and	byte [esp+8], 11111110b	; clear carry bit of eflags register
   113                              <1> 	;
   114 000060F2 80FC08              <1> 	cmp	ah, (RTC_TBE-RTC_TB)/4	; CHECK IF COMMAND IN VALID RANGE (0-7)
   115 000060F5 F5                  <1> 	cmc				; COMPLEMENT CARRY FOR ERROR EXIT
   116                              <1> 	; (*) jc short TIME_9		; EXIT WITH CARRY = 1 IF NOT VALID
   117 000060F6 721A                <1> 	jc	short _TIME_9 ; 29/05/2016
   118                              <1> 
   119 000060F8 1E                  <1> 	push	ds
   120 000060F9 56                  <1> 	push	esi
   121 000060FA 66BE1000            <1> 	mov	si, KDATA		; kernel data segment
   122 000060FE 8EDE                <1> 	mov	ds, si
   123                              <1> 
   124                              <1> 	;;15/01/2017
   125                              <1> 	; 14/01/2017
   126                              <1> 	; 02/01/2017
   127                              <1> 	;;mov	byte [intflg], 35h	; date & time interrupt 
   128                              <1> 	;sti
   129                              <1> 	;
   130 00006100 C0E402              <1> 	shl	ah, 2			; convert function to dword offset
   131 00006103 0FB6F4              <1> 	movzx	esi, ah			; PLACE INTO ADDRESSING REGISTER
   132                              <1> 	;cli				; NO INTERRUPTS DURING TIME FUNCTIONS
   133 00006106 FF96[18610000]      <1> 	call	[esi+RTC_TB]		; VECTOR TO FUNCTION REQUESTED WITH CY=0
   134                              <1> 					; RETURN WITH CARRY FLAG SET FOR RESULT
   135                              <1> 	;sti				; INTERRUPTS BACK ON
   136 0000610C B400                <1> 	mov	ah, 0			; CLEAR (AH) TO ZERO
   137 0000610E 5E                  <1> 	pop	esi			; RECOVER USERS REGISTER
   138 0000610F 1F                  <1> 	pop	ds			; RECOVER USERS SEGMENT SELECTOR
   139                              <1> 
   140                              <1> 	;;15/01/2017
   141                              <1> 	; 02/01/2017
   142                              <1> 	;;mov	byte [ss:intflg], 0 ; 07/01/2017
   143                              <1> 
   144                              <1> ;TIME_9:
   145                              <1> 					; RETURN WITH CY= 0 IF NO ERROR
   146                              <1> 	; (*) 29/05/2016
   147                              <1> 	; (*) retf 4 ; skip eflags on stack
   148 00006110 7305                <1> 	jnc	short _TIME_10
   149                              <1> _TIME_9:
   150                              <1> 	; 29/05/2016 -set carry flag on stack-
   151                              <1> 	; [esp] = EIP
   152                              <1> 	; [esp+4] = CS
   153                              <1> 	; [esp+8] = E-FLAGS
   154 00006112 804C240801          <1> 	or	byte [esp+8], 1	 ; set carry bit of eflags register
   155                              <1> 	; [esp+12] = ESP (user)
   156                              <1> 	; [esp+16] = SS (User)
   157                              <1> _TIME_10:
   158 00006117 CF                  <1> 	iretd
   159                              <1> 	
   160                              <1> 	; (*) 29/05/2016 - 'ref 4' intruction causes to stack fault
   161                              <1> 	; (OUTER-PRIVILEGE-LEVEL)
   162                              <1> 	; INTEL 80386 PROGRAMMER'S REFERENCE MANUAL 1986
   163                              <1> 	; // RETF instruction:
   164                              <1> 	;
   165                              <1> 	; IF OperandMode=32 THEN
   166                              <1>  	;    Load CS:EIP from stack;
   167                              <1>  	;    Set CS RPL to CPL;
   168                              <1>  	;    Increment eSP by 8 plus the immediate offset if it exists;
   169                              <1>  	;    Load SS:eSP from stack;
   170                              <1>  	; ELSE (* OperandMode=16 *)
   171                              <1>  	;    Load CS:IP from stack;
   172                              <1>  	;    Set CS RPL to CPL;
   173                              <1>  	;    Increment eSP by 4 plus the immediate offset if it exists;
   174                              <1> 	;    Load SS:eSP from stack;
   175                              <1>  	; FI;
   176                              <1> 	;
   177                              <1> 	; //					
   178                              <1> 					; ROUTINE VECTOR TABLE (AH)=
   179                              <1> RTC_TB:
   180 00006118 [38610000]          <1> 	dd	RTC_00			; 0 = READ CURRENT CLOCK COUNT
   181 0000611C [4B610000]          <1> 	dd	RTC_10			; 1 = SET CLOCK COUNT
   182 00006120 [59610000]          <1> 	dd	RTC_20			; 2 = READ THE REAL TIME CLOCK TIME
   183 00006124 [88610000]          <1> 	dd	RTC_30			; 3 = SET REAL TIME CLOCK TIME
   184 00006128 [CA610000]          <1> 	dd	RTC_40			; 4 = READ THE REAL TIME CLOCK DATE
   185 0000612C [F7610000]          <1> 	dd	RTC_50			; 5 = SET REAL TIME CLOCK DATE
   186 00006130 [44620000]          <1> 	dd	RTC_60			; 6 = SET THE REAL TIME CLOCK ALARM
   187 00006134 [97620000]          <1> 	dd	RTC_70			; 7 = RESET ALARM
   188                              <1> 
   189                              <1> RTC_TBE	equ	$
   190                              <1> 
   191                              <1> RTC_00:				; READ TIME COUNT
   192 00006138 A0[045F0100]        <1> 	mov	al, [TIMER_OFL]		; GET THE OVERFLOW FLAG
   193 0000613D C605[045F0100]00    <1> 	mov	byte [TIMER_OFL], 0	; AND THEN RESET THE OVERFLOW FLAG
   194 00006144 8B0D[005F0100]      <1>         mov     ecx, [TIMER_LH]         ; GET COUNT OF TIME
   195 0000614A C3                  <1> 	retn
   196                              <1> 
   197                              <1> RTC_10:				; SET TIME COUNT
   198 0000614B 890D[005F0100]      <1>         mov     [TIMER_LH], ecx         ; SET TIME COUNT
   199 00006151 C605[045F0100]00    <1> 	mov	byte [TIMER_OFL], 0	; RESET OVERFLOW FLAG
   200 00006158 C3                  <1> 	retn				; RETURN WITH NO CARRY
   201                              <1> 
   202                              <1> RTC_20:				; GET RTC TIME
   203 00006159 E8EB010000          <1> 	call	UPD_IPR			; CHECK FOR UPDATE IN PROCESS
   204 0000615E 7227                <1> 	jc	short RTC_29		; EXIT IF ERROR (CY= 1)
   205                              <1> 
   206 00006160 B000                <1> 	mov	al, CMOS_SECONDS	; SET ADDRESS OF SECONDS
   207 00006162 E8FD010000          <1> 	call	CMOS_READ		; GET SECONDS
   208 00006167 88C6                <1> 	mov	dh, al			; SAVE
   209 00006169 B00B                <1> 	mov	al, CMOS_REG_B		; ADDRESS ALARM REGISTER
   210 0000616B E8F4010000          <1> 	call	CMOS_READ		; READ CURRENT VALUE OF DSE BIT
   211 00006170 2401                <1> 	and	al, 00000001b		; MASK FOR VALID DSE BIT
   212 00006172 88C2                <1> 	mov	dl, al			; SET [DL] TO ZERO FOR NO DSE BIT
   213 00006174 B002                <1> 	mov	al, CMOS_MINUTES	; SET ADDRESS OF MINUTES
   214 00006176 E8E9010000          <1> 	call	CMOS_READ		; GET MINUTES
   215 0000617B 88C1                <1> 	mov	cl, al			; SAVE
   216 0000617D B004                <1>         mov     al, CMOS_HOURS          ; SET ADDRESS OF HOURS
   217 0000617F E8E0010000          <1> 	call	CMOS_READ		; GET HOURS
   218 00006184 88C5                <1> 	mov	ch, al			; SAVE
   219 00006186 F8                  <1> 	clc				; SET CY= 0
   220                              <1> RTC_29:
   221 00006187 C3                  <1> 	retn				; RETURN WITH RESULT IN CARRY FLAG
   222                              <1> 
   223                              <1> RTC_30:				; SET RTC TIME
   224 00006188 E8BC010000          <1> 	call	UPD_IPR			; CHECK FOR UPDATE IN PROCESS
   225 0000618D 7305                <1> 	jnc	short RTC_35		; GO AROUND IF CLOCK OPERATING
   226 0000618F E817010000          <1> 	call	RTC_STA			; ELSE TRY INITIALIZING CLOCK
   227                              <1> RTC_35:
   228 00006194 88F4                <1> 	mov	ah, dh			; GET TIME BYTE - SECONDS
   229 00006196 B000                <1> 	mov	al, CMOS_SECONDS	; ADDRESS SECONDS
   230 00006198 E8E0010000          <1> 	call	CMOS_WRITE		; UPDATE SECONDS
   231 0000619D 88CC                <1> 	mov	ah, cl			; GET TIME BYTE - MINUTES
   232 0000619F B002                <1> 	mov	al, CMOS_MINUTES	; ADDRESS MINUTES
   233 000061A1 E8D7010000          <1> 	call	CMOS_WRITE		; UPDATE MINUTES
   234 000061A6 88EC                <1> 	mov	ah, ch			; GET TIME BYTE - HOURS
   235 000061A8 B004                <1> 	mov	al, CMOS_HOURS		; ADDRESS HOURS
   236 000061AA E8CE010000          <1> 	call	CMOS_WRITE		; UPDATE ADDRESS
   237                              <1> 	;mov	al, CMOS_REG_B		; ADDRESS ALARM REGISTER
   238                              <1> 	;mov	ah, al
   239 000061AF 66B80B0B            <1> 	mov	ax, CMOS_REG_B * 257
   240 000061B3 E8AC010000          <1> 	call	CMOS_READ		; READ CURRENT TIME
   241 000061B8 2462                <1> 	and	al, 01100010b		; MASK FOR VALID BIT POSITIONS
   242 000061BA 0C02                <1> 	or	al, 00000010b		; TURN ON 24 HOUR MODE
   243 000061BC 80E201              <1> 	and	dl, 00000001b		; USE ONLY THE DSE BIT
   244 000061BF 08D0                <1> 	or	al, dl			; GET DAY LIGHT SAVINGS TIME BIT (OSE)
   245 000061C1 86E0                <1> 	xchg	ah, al			; PLACE IN WORK REGISTER AND GET ADDRESS
   246 000061C3 E8B5010000          <1> 	call	CMOS_WRITE		; SET NEW ALARM SITS
   247 000061C8 F8                  <1> 	clc				; SET CY= 0
   248 000061C9 C3                  <1> 	retn				; RETURN WITH CY= 0
   249                              <1> 
   250                              <1> RTC_40:				; GET RTC DATE
   251 000061CA E87A010000          <1> 	call	UPD_IPR			; CHECK FOR UPDATE IN PROCESS
   252 000061CF 7225                <1> 	jc	short RTC_49		; EXIT IF ERROR (CY= 1)
   253                              <1> 
   254 000061D1 B007                <1> 	mov	al, CMOS_DAY_MONTH	; ADDRESS DAY OF MONTH
   255 000061D3 E88C010000          <1> 	call	CMOS_READ		; READ DAY OF MONTH
   256 000061D8 88C2                <1> 	mov	dl, al			; SAVE
   257 000061DA B008                <1> 	mov	al, CMOS_MONTH		; ADDRESS MONTH
   258 000061DC E883010000          <1> 	call	CMOS_READ		; READ MONTH
   259 000061E1 88C6                <1> 	mov	dh, al			; SAVE
   260 000061E3 B009                <1> 	mov	al, CMOS_YEAR		; ADDRESS YEAR
   261 000061E5 E87A010000          <1> 	call	CMOS_READ		; READ YEAR
   262 000061EA 88C1                <1> 	mov	cl, al			; SAVE
   263 000061EC B032                <1> 	mov	al, CMOS_CENTURY	; ADDRESS CENTURY LOCATION
   264 000061EE E871010000          <1> 	call	CMOS_READ		; GET CENTURY BYTE
   265 000061F3 88C5                <1> 	mov	ch, al			; SAVE
   266 000061F5 F8                  <1> 	clc				; SET CY=0
   267                              <1> RTC_49:
   268 000061F6 C3                  <1> 	retn				; RETURN WITH RESULTS IN CARRY FLAG
   269                              <1> 
   270                              <1> RTC_50:				; SET RTC DATE
   271 000061F7 E84D010000          <1> 	call	UPD_IPR			; CHECK FOR UPDATE IN PROCESS
   272 000061FC 7305                <1> 	jnc	short RTC_55		; GO AROUND IF NO ERROR
   273 000061FE E8A8000000          <1> 	call	RTC_STA			; ELSE INITIALIZE CLOCK
   274                              <1> RTC_55:
   275 00006203 66B80600            <1> 	mov	ax, CMOS_DAY_WEEK	; ADDRESS OF DAY OF WEEK BYTE
   276 00006207 E871010000          <1> 	call	CMOS_WRITE		; LOAD ZEROS TO DAY OF WEEK
   277 0000620C 88D4                <1> 	mov	ah, dl			; GET DAY OF MONTH BYTE
   278 0000620E B007                <1> 	mov	al, CMOS_DAY_MONTH	; ADDRESS DAY OF MONTH BYTE
   279 00006210 E868010000          <1> 	call	CMOS_WRITE		; WRITE OF DAY OF MONTH REGISTER
   280 00006215 88F4                <1> 	mov	ah, dh			; GET MONTH
   281 00006217 B008                <1> 	mov	al, CMOS_MONTH		; ADDRESS MONTH BYTE
   282 00006219 E85F010000          <1> 	call	CMOS_WRITE		; WRITE MONTH REGISTER
   283 0000621E 88CC                <1> 	mov	ah, cl			; GET YEAR BYTE
   284 00006220 B009                <1> 	mov	al, CMOS_YEAR		; ADDRESS YEAR REGISTER
   285 00006222 E856010000          <1> 	call	CMOS_WRITE		; WRITE YEAR REGISTER
   286 00006227 88EC                <1> 	mov	ah, ch			; GET CENTURY BYTE
   287 00006229 B032                <1> 	mov	al, CMOS_CENTURY	; ADDRESS CENTURY BYTE
   288 0000622B E84D010000          <1> 	call	CMOS_WRITE		; WRITE CENTURY LOCATION
   289                              <1> 	;mov	al, CMOS_REG_B		; ADDRESS ALARM REGISTER
   290                              <1> 	;mov	ah, al
   291 00006230 66B80B0B            <1> 	mov	ax, CMOS_REG_B * 257
   292 00006234 E82B010000          <1> 	call	CMOS_READ		; READ WIRRENT SETTINGS
   293 00006239 247F                <1> 	and	al, 07Fh		; CLEAR 'SET BIT'
   294 0000623B 86E0                <1> 	xchg	ah, al			; MOVE TO WORK REGISTER
   295 0000623D E83B010000          <1> 	call	CMOS_WRITE		; AND START CLOCK UPDATING
   296 00006242 F8                  <1> 	clc				; SET CY= 0
   297 00006243 C3                  <1> 	retn				; RETURN CY=0
   298                              <1> 
   299                              <1> RTC_60:				; SET RTC ALARM
   300 00006244 B00B                <1> 	mov	al, CMOS_REG_B		; ADDRESS ALARM
   301 00006246 E819010000          <1> 	call	CMOS_READ		; READ ALARM REGISTER
   302 0000624B A820                <1> 	test	al, 20h			; CHECK FOR ALARM ALREADY ENABLED
   303 0000624D F9                  <1> 	stc				; SET CARRY IN CASE OF ERROR
   304 0000624E 7542                <1> 	jnz	short RTC_69		; ERROR EXIT IF ALARM SET
   305 00006250 E8F4000000          <1> 	call	UPD_IPR			; CHECK FOR UPDATE IN PROCESS
   306 00006255 7305                <1> 	jnc	short RTC_65		; SKIP INITIALIZATION IF NO ERROR
   307 00006257 E84F000000          <1> 	call	RTC_STA			; ELSE INITIALIZE CLOCK
   308                              <1> RTC_65:	
   309 0000625C 88F4                <1> 	mov	ah, dh			; GET SECONDS BYTE
   310 0000625E B001                <1> 	mov	al, CMOS_SEC_ALARM	; ADDRESS THE SECONDS ALARM REGISTER
   311 00006260 E818010000          <1> 	call	CMOS_WRITE		; INSERT SECONDS
   312 00006265 88CC                <1> 	mov	ah, cl			; GET MINUTES PARAMETER
   313 00006267 B003                <1> 	mov	al, CMOS_MIN_ALARM	; ADDRESS MINUTES ALARM REGISTER
   314 00006269 E80F010000          <1> 	call	CMOS_WRITE		; INSERT MINUTES
   315 0000626E 88EC                <1> 	mov	ah, ch			; GET HOURS PARAMETER
   316 00006270 B005                <1> 	mov	al, CMOS_HR_ALARM	; ADDRESS HOUR ALARM REGISTER
   317 00006272 E806010000          <1> 	call	CMOS_WRITE		; INSERT HOURS
   318 00006277 E4A1                <1> 	in	al, INTB01		; READ SECOND INTERRUPT MASK REGISTER
   319 00006279 24FE                <1> 	and	al, 0FEh		; ENABLE ALARM TIMER BIT (CY= 0)
   320 0000627B E6A1                <1> 	out	INTB01, al		; WRITE UPDATED MASK
   321                              <1> 	;mov	al, CMOS_REG_B		; ADDRESS ALARM REGISTER
   322                              <1> 	;mov	ah, al
   323 0000627D 66B80B0B            <1> 	mov	ax, CMOS_REG_B * 257
   324 00006281 E8DE000000          <1> 	call	CMOS_READ		; READ CURRENT ALARM REGISTER
   325 00006286 247F                <1> 	and	al, 07Fh		; ENSURE SET BIT TURNED OFF
   326 00006288 0C20                <1> 	or	al, 20h			; TURN ON ALARM ENABLE
   327 0000628A 86E0                <1> 	xchg	ah, al			; MOVE MASK TO OUTPUT REGISTER
   328 0000628C E8EC000000          <1> 	call	CMOS_WRITE		; WRITE NEW ALARM MASK
   329 00006291 F8                  <1> 	clc				; SET CY= 0
   330                              <1> RTC_69:
   331 00006292 66B80000            <1> 	mov	ax, 0			; CLEAR AX REGISTER
   332 00006296 C3                  <1> 	retn				; RETURN WITH RESULTS IN CARRY FLAC
   333                              <1> 
   334                              <1> RTC_70:				; RESET ALARM
   335                              <1> 	;mov	al, CMOS_REG_B		; ADDRESS ALARM REGISTER
   336                              <1> 	;mov	ah, al
   337 00006297 66B80B0B            <1> 	mov	ax, CMOS_REG_B * 257	; ADDRESS ALARM REGISTER (TO BOTH AH,AL)
   338 0000629B E8C4000000          <1> 	call	CMOS_READ		; READ ALARM REGISTER
   339 000062A0 2457                <1> 	and	al, 57h			; TURN OFF ALARM ENABLE
   340 000062A2 86E0                <1> 	xchg	ah, al			; SAVE DATA AND RECOVER ADDRESS
   341 000062A4 E8D4000000          <1> 	call	CMOS_WRITE		; RESTORE NEW VALUE
   342 000062A9 F8                  <1> 	clc				; SET CY= 0
   343 000062AA C3                  <1> 	retn				; RETURN WITH NO CARRY
   344                              <1> 
   345                              <1> RTC_STA:			; INITIALIZE REAL TIME CLOCK
   346                              <1> 	;mov	al, CMOS_REG_A		; ADDRESS REGISTER A AND LOAD DATA MASK		
   347                              <1> 	;mov	ah, 26h
   348 000062AB 66B80A26            <1> 	mov	ax, (26h*100h)+CMOS_REG_A
   349 000062AF E8C9000000          <1> 	call	CMOS_WRITE		; INITIALIZE STATUS REGISTER A
   350                              <1> 	;mov	al, CMOS_REG_B		; SET "SET BIT" FOR CLOCK INITIALIZATION	
   351                              <1> 	;mov	ah, 82h
   352 000062B4 66B80B82            <1> 	mov	ax, (82h*100h)+CMOS_REG_B
   353 000062B8 E8C0000000          <1> 	call	CMOS_WRITE		; AND 24 HOUR MODE TO REGISTER B
   354 000062BD B00C                <1> 	mov	al, CMOS_REG_C		; ADDRESS REGISTER C
   355 000062BF E8A0000000          <1> 	call	CMOS_READ		; READ REGISTER C TO INITIALIZE
   356 000062C4 B00D                <1> 	mov	al, CMOS_REG_D		; ADDRESS REGISTER D
   357 000062C6 E899000000          <1> 	call	CMOS_READ		; READ REGISTER D TO INITIALIZE
   358 000062CB C3                  <1> 	retn
   359                              <1> 
   360                              <1> ; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
   361                              <1> 
   362                              <1> ;--- HARDWARE INT  70 H -- ( IRQ LEVEL  8) --------------------------------------
   363                              <1> ; ALARM INTERRUPT HANDLER (RTC)							:
   364                              <1> ;       THIS ROUTINE HANDLES THE PERIODIC AND ALARM INTERRUPTS FROM THE CMOS	:
   365                              <1> ;       TIMER. INPUT FREQUENCY IS 1.024 KHZ OR APPROXIMATELY 1024 INTERRUPTS	:
   366                              <1> ;       EVERY SECOND FOR THE PERIODIC INTERRUPT. FOR THE ALARM FUNCTION,	:
   367                              <1> ;       THE INTERRUPT WILL OCCUR AT THE DESIGNATED TIME.			:
   368                              <1> ;										:
   369                              <1> ;       INTERRUPTS ARE ENABLED WHEN THE EVENT OR ALARM FUNCTION IS ACTIVATED.	:
   370                              <1> ;       FOR THE EVENT INTERRUPT, THE HANDLER WILL DECREMENT THE WAIT COUNTER	:
   371                              <1> ;       AND WHEN IT EXPIRES WILL SET THE DESIGNATED LOCATION TO 80H. FOR	:
   372                              <1> ;       THE ALARM INTERRUPT. THE USER MUST PROVIDE A ROUTINE TO INTERCEPT	:
   373                              <1> ;       THE CORRECT ADDRESS FROM THE VECTOR TABLE INVOKED BY INTERRUPT 4AH	:
   374                              <1> ;       PRIOR TO SETTING THE REAL TIME CLOCK ALARM (INT 1AH, AH= 06H).		:
   375                              <1> ;--------------------------------------------------------------------------------
   376                              <1> 
   377                              <1> RTC_A_INT: ; 07/01/2017
   378                              <1> ;RTC_INT:				; ALARM INTERRUPT
   379 000062CC 1E                  <1> 	push	ds			; LEAVE INTERRUPTS DISABLED
   380 000062CD 50                  <1> 	push	eax			; SAVE REGISTERS
   381 000062CE 57                  <1> 	push	edi
   382                              <1> RTC_I_1:				; CHECK FOR SECOND INTERRUPT
   383 000062CF 66B88C8B            <1> 	mov	ax, 256*(CMOS_REG_B+NMI)+CMOS_REG_C+NMI ; ALARM AND STATUS
   384 000062D3 E670                <1> 	out	CMOS_PORT, al		; WRITE ALARM FLAG MASK ADDRESS
   385 000062D5 90                  <1> 	nop				; I/O DELAY
   386 000062D6 EB00                <1> 	jmp	short $+2
   387 000062D8 E471                <1> 	in	al, CMOS_DATA		; READ AND RESET INTERRUPT REQUEST FLAGS
   388 000062DA A860                <1> 	test	al, 01100000b		; CHECK FOR EITHER INTERRUPT PENDING
   389 000062DC 745D                <1> 	jz	short	RTC_I_9		; EXIT IF NOT A VALID RTC INTERRUPT
   390                              <1> 
   391 000062DE 86E0                <1> 	xchg	ah, al			; SAVE FLAGS AND GET ENABLE ADDRESS
   392 000062E0 E670                <1> 	out	CMOS_PORT, al		; WRITE ALARM ENABLE MASK ADDRESS
   393 000062E2 90                  <1> 	nop				; I/O DELAY
   394 000062E3 EB00                <1> 	jmp	short $+2	
   395 000062E5 E471                <1> 	in	al, CMOS_DATA		; READ CURRENT ALARM ENABLE MASK
   396 000062E7 20E0                <1> 	and	al, ah			; ALLOW ONLY SOURCES THAT ARE ENABLED
   397 000062E9 A840                <1> 	test	al, 01000000b		; CHECK FOR PERIODIC INTERRUPT
   398 000062EB 743B                <1> 	jz	short RTC_I_5		; SKIP IF NOT A PERIODIC INTERRUPT
   399                              <1> 
   400                              <1> ;-----	DECREMENT WAIT COUNT BY INTERRUPT INTERVAL
   401                              <1> 
   402 000062ED 66BF1000            <1> 	mov	di, KDATA		; kernel data segment
   403 000062F1 8EDF                <1> 	mov	ds, di
   404                              <1> 	
   405 000062F3 812D[F85E0100]D003- <1> 	sub	dword [RTC_LH], 976	; DECREMENT COUNT BY 1/1024
   405 000062FB 0000                <1>
   406 000062FD 7329                <1> 	jnc	short RTC_I_5		; SKIP TILL 32 BIT WORD LESS THAN ZERO
   407                              <1> 
   408                              <1> ;-----	TURN OFF PERIODIC INTERRUPT ENABLE
   409                              <1> 
   410 000062FF 6650                <1> 	push	ax			; SAVE INTERRUPT FLAG MASK
   411 00006301 66B88B8B            <1> 	mov	ax, 257*(CMOS_REG_B+NMI) ; INTERRUPT ENABLE REGISTER
   412 00006305 E670                <1> 	out	CMOS_PORT, al		; WRITE ADDRESS TO CMOS CLOCK
   413 00006307 90                  <1> 	nop				; I/O DELAY
   414 00006308 EB00                <1> 	jmp	short $+2
   415 0000630A E471                <1> 	in	al, CMOS_DATA		; READ CURRENT ENABLES
   416 0000630C 24BF                <1> 	and	al, 0BFh		; TURN OFF PIE
   417 0000630E 86C4                <1> 	xchg	al, ah			; GET CMOS ADDRESS AND SAVE VALUE
   418 00006310 E670                <1> 	out	CMOS_PORT, al		; ADDRESS REGISTER B
   419 00006312 86C4                <1> 	xchg	al, ah			; GET NEW INTERRUPT ENABLE MASK
   420 00006314 E671                <1> 	out	CMOS_DATA, al		; SET MASK IN INTERRUPT ENABLE REGISTER
   421 00006316 C605[FC5E0100]00    <1> 	mov	byte [RTC_WAIT_FLAG], 0	; SET FUNCTION ACTIVE FLAG OFF
   422 0000631D 8B3D[FD5E0100]      <1> 	mov	edi, [USER_FLAG]	; SET UP (DS:DI) TO POINT TO USER FLAG
   423 00006323 C60780              <1> 	mov	byte [edi], 80h		; TURN ON USERS FLAG
   424 00006326 6658                <1> 	pop	ax			; GET INTERRUPT SOURCE BACK
   425                              <1> RTC_I_5:
   426 00006328 A820                <1> 	test	al, 00100000b		; TEST FOR ALARM INTERRUPT
   427 0000632A 740D                <1> 	jz	short RTC_I_7		; SKIP USER INTERRUPT CALL IF NOT ALARM
   428                              <1> 
   429 0000632C B00D                <1> 	mov	al, CMOS_REG_D		; POINT TO DEFAULT READ ONLY REGISTER
   430 0000632E E670                <1> 	out	CMOS_PORT, al		; ENABLE NMI AND CMOS ADDRESS TO DEFAULT
   431 00006330 FB                  <1> 	sti				; INTERRUPTS BACK ON NOW
   432 00006331 52                  <1> 	push	edx
   433 00006332 E8879C0000          <1> 	call	INT4Ah			; TRANSFER TO USER ROUTINE
   434 00006337 5A                  <1> 	pop	edx
   435 00006338 FA                  <1> 	cli				; BLOCK INTERRUPT FOR RETRY
   436                              <1> RTC_I_7:				; RESTART ROUTINE TO HANDLE DELAYED
   437 00006339 EB94                <1> 	jmp	short RTC_I_1		;  ENTRY AND SECOND EVENT BEFORE DONE
   438                              <1> 
   439                              <1> RTC_I_9:				; EXIT - NO PENDING INTERRUPTS
   440 0000633B B00D                <1> 	mov	al, CMOS_REG_D		; POINT TO DEFAULT READ ONLY REGISTER
   441 0000633D E670                <1> 	out	CMOS_PORT, al		; ENABLE NMI AND CMOS ADDRESS TO DEFAULT
   442 0000633F B020                <1> 	mov	al, EOI			; END OF INTERRUPT MASK TO 8259 - 2
   443 00006341 E6A0                <1> 	out	INTB00, al		; TO 8259 - 2
   444 00006343 E620                <1> 	out	INTA00,	al		; TO 8259 - 1
   445 00006345 5F                  <1> 	pop	edi			; RESTORE REGISTERS
   446 00006346 58                  <1> 	pop	eax
   447 00006347 1F                  <1> 	pop	ds
   448 00006348 CF                  <1> 	iretd				; END OF INTERRUPT
   449                              <1> 
   450                              <1> 	
   451                              <1> 	; 29/05/2016 - TRDOS 386 (TRDOS v2.0)
   452                              <1> 	; 22/08/2014 (Retro UNIX 386 v1)
   453                              <1> 	; IBM PC/AT BIOS source code ----- 10/06/85 (bios2.asm)
   454                              <1> UPD_IPR:				; WAIT TILL UPDATE NOT IN PROGRESS
   455 00006349 51                  <1> 	push	ecx
   456                              <1> 
   457                              <1> 	; 29/05/2016
   458 0000634A B968110000          <1> 	mov	ecx, ((1984+244)*4)/2	; AWARD BIOS 1999, ATIME.ASM		
   459                              <1> 					; 'WAITCPU_CK_UD_STAT'
   460                              <1> 					; (244Us + 1984Us)
   461                              <1> 					; (assume each read takes
   462                              <1> 					;  2 microseconds).
   463                              <1> 	;mov	ecx, 65535		
   464                              <1> 		;mov cx, 800		; SET TIMEOUT LOOP COUNT (= 800)	
   465                              <1> UPD_10:
   466 0000634F B00A                <1> 	mov	al, CMOS_REG_A		; ADDRESS STATUS REGISTER A
   467 00006351 FA                  <1> 	cli				; NO TIMER INTERRUPTS DURING UPDATES
   468 00006352 E80D000000          <1> 	call	CMOS_READ		; READ UPDATE IN PROCESS FLAG
   469 00006357 A880                <1> 	test	al, 80h			; IF UIP BIT IS ON ( CANNOT READ TIME )
   470 00006359 7406                <1> 	jz	short UPD_90		; EXIT WITH CY= 0 IF CAN READ CLOCK NOW
   471 0000635B FB                  <1> 	sti				; ALLOW INTERRUPTS WHILE WAITING
   472 0000635C E2F1                <1> 	loop	UPD_10			; LOOP TILL READY OR TIMEOUT
   473 0000635E 31C0                <1> 	xor	eax, eax		; CLEAR RESULTS IF ERROR
   474                              <1> 		; xor ax, ax
   475 00006360 F9                  <1> 	stc				; SET CARRY FOR ERROR
   476                              <1> UPD_90:
   477 00006361 59                  <1> 	pop	ecx			; RESTORE CALLERS REGISTER
   478 00006362 FA                  <1> 	cli				; INTERRUPTS OFF DURING SET
   479 00006363 C3                  <1> 	retn				; RETURN WITH CY FLAG SET
   480                              <1> 
   481                              <1> 
   482                              <1> 	; 29/05/2016 - TRDOS 386 (TRDOS v2.0) 
   483                              <1> 	; 22/08/2014 (Retro UNIX 386 v1)
   484                              <1> 	; IBM PC/AT BIOS source code ----- 10/06/85 (test4.asm)
   485                              <1> 
   486                              <1> ;--- CMOS_READ -----------------------------------------------------------------
   487                              <1> ;		READ BYTE FROM CMOS_SYSTEM CLOCK CONFIGURATION TABLE	       :
   488                              <1> ;									       :
   489                              <1> ; INPUT: (AL)=	CMOS_TABLE ADDRESS TO BE READ				       :
   490                              <1> ;		BIT    7 = 0 FOR NMI ENABLED AND 1 FOR NMI DISABLED ON EXIT    :
   491                              <1> ;		BITS 6-0 = ADDRESS OF TABLE LOCATION TO READ		       :
   492                              <1> ;									       :
   493                              <1> ; OUTPUT: (AL)	VALUE AT LOCATION (AL) MOVED INTO (AL). IF BIT 7 OF (AL) WAS   :
   494                              <1> ;		ON THEN NMI LEFT DISABLED, DURING THE CMOS READ BOTH NMI AND   :
   495                              <1> ;		NORMAL INTERRUPTS ARE DISABLED TO PROTECT CMOS DATA INTEGRITY. :
   496                              <1> ;		THE CMOS ADDRESS REGISTER IS POINTED TO A DEFAULT VALUE AND    :
   497                              <1> ;		THE INTERRUPT FLAG RESTORED TO THE ENTRY STATE ON RETURN.      :
   498                              <1> ;		ONLY THE (AL) REGISTER AND THE NMI STATE IS CHANGED.	       :
   499                              <1> ;-------------------------------------------------------------------------------
   500                              <1> 
   501                              <1> CMOS_READ:
   502 00006364 9C                  <1> 	pushf				; SAVE INTERRUPT ENABLE STATUS AND FLAGS
   503 00006365 D0C0                <1> 	rol	al, 1			; MOVE NMI BIT TO LOW POSITION
   504 00006367 F9                  <1> 	stc				; FORCE NMI BIT ON IN CARRY FLAG
   505 00006368 D0D8                <1> 	rcr	al, 1			; HIGH BIT ON TO DISABLE NMI - OLD IN CY
   506 0000636A FA                  <1> 	cli				; DISABLE INTERRUPTS
   507 0000636B E670                <1> 	out	CMOS_PORT, al		; ADDRESS LOCATION AND DISABLE NMI
   508                              <1> 	; 29/05/2016
   509                              <1> 	;nop				; I/O DELAY
   510 0000636D E6EB                <1> 	out	0ebh,al	; NEWIODELAY ; AWARD BIOS 1999, ATIME.ASM
   511                              <1> 	;
   512 0000636F E471                <1> 	in	al, CMOS_DATA		; READ THE REQUESTED CMOS LOCATION
   513 00006371 6650                <1> 	push	ax			; SAVE (AH) REGISTER VALUE AND CMOS BYTE
   514                              <1> 	; 15/03/2015 ; IBM PC/XT Model 286 BIOS source code 
   515                              <1> 		     ; ----- 10/06/85 (test4.asm)
   516 00006373 B01E                <1> 	mov	al, CMOS_SHUT_DOWN*2 	; GET ADDRESS OF DEFAULT LOCATION
   517                              <1> 	;mov	al, CMOS_REG_D*2 	; GET ADDRESS OF DEFAULT LOCATION
   518 00006375 D0D8                <1> 	rcr	al, 1			; PUT ORIGINAL NMI MASK BIT INTO ADDRESS
   519 00006377 E670                <1> 	out	CMOS_PORT, al		; SET DEFAULT TO READ ONLY REGISTER
   520 00006379 6658                <1> 	pop	ax			; RESTORE (AH) AND (AL), CMOS BYTE
   521 0000637B 9D                  <1> 	popf	
   522 0000637C C3                  <1> 	retn				; RETURN WITH FLAGS RESTORED
   523                              <1> 
   524                              <1> ; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
   525                              <1> 
   526                              <1> ;--- CMOS_WRITE ----------------------------------------------------------------
   527                              <1> ;	WRITE BYTE TO CMOS SYSTEM CLOCK CONFIGURATION TABLE		       :
   528                              <1> ;									       :
   529                              <1> ; INPUT: (AL)=	CMOS TABLE ADDRESS TO BE WRITTEN TO			       :
   530                              <1> ;		BIT    7 = 0 FOR NMI ENABLED AND 1 FOR NMI DISABLED ON EXIT    :
   531                              <1> ;		BITS 6-0 = ADDRESS OF TABLE LOCATION TO WRITE		       :
   532                              <1> ;	 (AH)=	NEW VALUE TO BE PLACED IN THE ADDRESSED TABLE LOCATION	       :
   533                              <1> ;									       :
   534                              <1> ; OUTPUT:	VALUE IN (AH) PLACED IN LOCATION (AL) WITH NMI LEFT DISABLED   :
   535                              <1> ;		IF BIT 7 OF (AL) IS ON, DURING THE CMOS UPDATE BOTH NMI AND    :
   536                              <1> ;		NORMAL INTERRUPTS ARE DISABLED TO PROTECT CMOS DATA INTEGRITY. :
   537                              <1> ;		THE CMOS ADDRESS REGISTER IS POINTED TO A DEFAULT VALUE AND    :
   538                              <1> ;		THE INTERRUPT FLAG RESTORED TO THE ENTRY STATE ON RETURN.      :
   539                              <1> ;		ONLY THE CMOS LOCATION AND THE NMI STATE IS CHANGED.	       :
   540                              <1> ;-------------------------------------------------------------------------------
   541                              <1> 
   542                              <1> CMOS_WRITE:				; WRITE (AH) TO LOCATION (AL)
   543 0000637D 9C                  <1> 	pushf				; SAVE INTERRUPT ENABLE STATUS AND FLAGS
   544 0000637E 6650                <1> 	push	ax			; SAVE WORK REGISTER VALUES
   545 00006380 D0C0                <1> 	rol	al, 1			; MOVE NMI BIT TO LOW POSITION
   546 00006382 F9                  <1> 	stc				; FORCE NMI BIT ON IN CARRY FLAG
   547 00006383 D0D8                <1> 	rcr	al, 1			; HIGH BIT ON TO DISABLE NMI - OLD IN CY
   548 00006385 FA                  <1> 	cli				; DISABLE INTERRUPTS
   549 00006386 E670                <1> 	out	CMOS_PORT, al		; ADDRESS LOCATION AND DISABLE NMI
   550 00006388 88E0                <1> 	mov	al, ah			; GET THE DATA BYTE TO WRITE
   551 0000638A E671                <1> 	out	CMOS_DATA, al		; PLACE IN REQUESTED CMOS LOCATION
   552 0000638C B01E                <1> 	mov	al, CMOS_SHUT_DOWN*2	; GET ADDRESS OF DEFAULT LOCATION
   553                              <1> 	;mov	al, CMOS_REG_D*2 	; GET ADDRESS OF DEFAULT LOCATION
   554 0000638E D0D8                <1> 	rcr	al, 1			; PUT ORIGINAL NMI MASK BIT INTO ADDRESS
   555 00006390 E670                <1> 	out	CMOS_PORT, al		; SET DEFAULT TO READ ONLY REGISTER
   556 00006392 90                  <1> 	nop				; I/O DELAY
   557 00006393 E471                <1> 	in	al, CMOS_DATA		; OPEN STANDBY LATCH
   558 00006395 6658                <1> 	pop	ax			; RESTORE WORK REGISTERS
   559 00006397 9D                  <1> 	popf
   560 00006398 C3                  <1> 	retn
   561                              <1> 
   562                              <1> ; /// End Of TIMER FUNCTIONS ///
  2677                                  
  2678 00006399 90<rept>                Align 16
  2679                                  
  2680                                  gdt:	; Global Descriptor Table
  2681                                  	; (30/07/2015, conforming cs)
  2682                                  	; (26/03/2015)
  2683                                  	; (24/03/2015, tss)
  2684                                  	; (19/03/2015)
  2685                                  	; (29/12/2013)
  2686                                  	;
  2687 000063A0 0000000000000000        	dw 0, 0, 0, 0		; NULL descriptor
  2688                                  	; 18/08/2014
  2689                                  			; 8h kernel code segment, base = 00000000h		
  2690                                  	;dw 0FFFFh, 0, 9E00h, 00CFh	; KCODE  ; 30/12/2016	 
  2691 000063A8 FFFF0000009ACF00        	dw 0FFFFh, 0, 9A00h, 00CFh	; KCODE
  2692                                  			; 10h kernel data segment, base = 00000000h	
  2693 000063B0 FFFF00000092CF00        	dw 0FFFFh, 0, 9200h, 00CFh	; KDATA
  2694                                  			; 1Bh user code segment, base address = 400000h ; CORE
  2695                                  	;dw 0FBFFh, 0, 0FE40h, 00CFh	; UCODE  ; 30/12/2016	
  2696 000063B8 FFFB000040FACF00        	dw 0FBFFh, 0, 0FA40h, 00CFh	; UCODE 
  2697                                  			; 23h user data segment, base address = 400000h ; CORE
  2698 000063C0 FFFB000040F2CF00        	dw 0FBFFh, 0, 0F240h, 00CFh	; UDATA
  2699                                  			; Task State Segment
  2700 000063C8 6700                    	dw 0067h ; Limit = 103 ; (104-1, tss size = 104 byte, 
  2701                                  			       ;  no IO permission in ring 3)
  2702                                  gdt_tss0:
  2703 000063CA 0000                    	dw 0  ; TSS base address, bits 0-15 
  2704                                  gdt_tss1:
  2705 000063CC 00                      	db 0  ; TSS base address, bits 16-23 
  2706                                  	      		; 49h	
  2707 000063CD E9                      	db 11101001b ; 0E9h => P=1/DPL=11/0/1/0/B/1 --> B = Task is busy (1)
  2708 000063CE 00                      	db 0 ; G/0/0/AVL/LIMIT=0000 ; (Limit bits 16-19 = 0000) (G=0, 1 byte)
  2709                                  gdt_tss2:
  2710 000063CF 00                      	db 0  ; TSS base address, bits 24-31 
  2711                                  
  2712                                  	; 30/11/2020
  2713                                  	; 29/11/2020 - TRDOS v2.0.3
  2714                                  	; VESA VBE3 VIDE BIOS 32 BIT PMI SEGMENTS (16 bit segments)
  2715                                  			; 30h ; VBE3CS
  2716                                  _vbe3_CS:  ; vesa vbe3 bios uses this as code seg (same addr with _vbe3_DS)
  2717                                  	; limit = 65536, base addr = 0, P/DPL/1/Type/C/R/A = 9Ah, 16 bit
  2718 000063D0 FFFF0000009A0000        	dw 0FFFFh, 0, 9A00h, 0 ; Note: base addr will be initialized
  2719                                  			; 38h ; VBE3BDS
  2720                                  _vbe3_BDS: ; vesa vbe3 bios uses this as equivalent of rombios data segment
  2721                                  	; limit = 1536, base addr = 0, P/DPL/1/Type/E/W/A = 92h, 16 bit
  2722 000063D8 FF05000000920000        	dw 05FFh, 0, 9200h, 0 ; Note: base addr will be initialized	
  2723                                  			; 40h ; VBE3A000 
  2724                                  _A0000Sel: ; VGA default video memory address
  2725                                  	; limit = 65536, base addr = 0A0000h, 16 bit
  2726 000063E0 FFFF00000A920000        	dw 0FFFFh, 0, 920Ah, 0
  2727                                  			; 48h ; VBE3B000 
  2728                                  _B0000Sel: ; MDA (monochrome) video memory address
  2729                                  	; limit = 65536, base addr = 0B0000h, 16 bit
  2730 000063E8 FFFF00000B920000        	dw 0FFFFh, 0, 920Bh, 0
  2731                                  			; 50h ; VBE3B800 
  2732                                  _B8000Sel: ; CGA video memory address
  2733                                  	; limit = 32768, base addr = 0B8000h, 16 bit
  2734 000063F0 FF7F00800B920000        	dw 07FFFh, 8000h, 920Bh, 0
  2735                                  			; 58h ; VBE3DS 
  2736                                  _vbe3_DS: ; vesa vbe3 bios uses this as data seg (CodeSegSel in PMInfoBlock)
  2737                                  	; limit = 65536, base addr = 0, P/DPL/1/Type/E/W/A = 92h, 16 bit
  2738 000063F8 FFFF000000920000        	dw 0FFFFh, 0, 9200h,0 ; Note: base addr will be initialized
  2739                                  			; 60h ; VBE3SS   
  2740                                  _vbe3_SS: ; kernel's stack segment but 16 bit version (same stack addr)
  2741                                  	; limit = 1024, base addr = 0, P/DPL/1/Type/E/W/A = 92h, 16 bit
  2742 00006400 FF03000000920000        	dw 03FFh, 0, 9200h, 0 ; Note: base addr will be initialized
  2743                                  			; 68h ; VBE3ES 	
  2744                                  _vbe3_ES: ; extra 16 bit segment points to buffers in kernel's mem space
  2745                                  	; limit = 2048, base addr = 0, P/DPL/1/Type/E/W/A = 92h, 16 bit
  2746 00006408 FF07000000920000        	dw 07FFh, 0, 9200h,0 ; Note: base addr will be initialized
  2747                                  			; 70h ; KODE16	
  2748                                  _16bit_CS: ; 16 bit code segment points to kernel's far return addr
  2749                                  	; limit = 16M, base addr = 0, P/DPL/1/Type/E/W/A = 92h, 16 bit
  2750 00006410 FFFF0000009AFF00        	dw 0FFFFh, 0, 9A00h, 00FFh ; Note: base addr will be initialized
  2751                                  
  2752                                  gdt_end:
  2753                                  	;; 9Eh = 1001 1110b (GDT byte 5) P=1/DPL=00/1/TYPE=1110, 
  2754                                  					;; Type= 1 (code)/C=1/R=1/A=0
  2755                                  		; P= Present, DPL=0=ring 0,  1= user (0= system)
  2756                                  		; 1= Code C= Conforming, R= Readable, A = Accessed
  2757                                  
  2758                                  	;; 9Ah = 1001 1010b (GDT byte 5) P=1/DPL=00/1/TYPE=1010, 
  2759                                  					;; Type= 1 (code)/C=0/R=1/A=0
  2760                                  		; P= Present, DPL=0=ring 0,  1= user (0= system)
  2761                                  		; 1= Code C= non-Conforming, R= Readable, A = Accessed
  2762                                  
  2763                                  	;; 92h = 1001 0010b (GDT byte 5) P=1/DPL=00/1/TYPE=1010, 
  2764                                  					;; Type= 0 (data)/E=0/W=1/A=0
  2765                                  		; P= Present, DPL=0=ring 0,  1= user (0= system)
  2766                                  		; 0= Data E= Expansion direction (1= down, 0= up)
  2767                                  		; W= Writeable, A= Accessed
  2768                                  
  2769                                  	;; FEh = 1111 1110b (GDT byte 5) P=1/DPL=11/1/TYPE=1110, 
  2770                                  					;; Type= 1 (code)/C=1/R=1/A=0
  2771                                  		; P= Present, DPL=3=ring 3,  1= user (0= system)
  2772                                  		; 1= Code C= Conforming, R= Readable, A = Accessed
  2773                                  	
  2774                                  	;; FAh = 1111 1010b (GDT byte 5) P=1/DPL=11/1/TYPE=1010, 
  2775                                  					;; Type= 1 (code)/C=0/R=1/A=0
  2776                                  		; P= Present, DPL=3=ring 3,  1= user (0= system)
  2777                                  		; 1= Code C= non-Conforming, R= Readable, A = Accessed
  2778                                  
  2779                                  	;; F2h = 1111 0010b (GDT byte 5) P=1/DPL=11/1/TYPE=0010, 
  2780                                  					;; Type= 0 (data)/E=0/W=1/A=0
  2781                                  		; P= Present, DPL=3=ring 3,  1= user (0= system)
  2782                                  		; 0= Data E= Expansion direction (1= down, 0= up)
  2783                                  	
  2784                                  	;; CFh = 1100 1111b (GDT byte 6) G=1/B=1/0/AVL=0, Limit=1111b (3)
  2785                                  
  2786                                  		;; Limit = FFFFFh (=> FFFFFh+1= 100000h) // bits 0-15, 48-51 //
  2787                                  		;	 = 100000h * 1000h (G=1) = 4GB
  2788                                  		;; Limit = FFBFFh (=> FFBFFh+1= FFC00h) // bits 0-15, 48-51 //
  2789                                  		;	 = FFC00h * 1000h (G=1) = 4GB - 4MB
  2790                                  		; G= Granularity (1= 4KB), B= Big (32 bit), 
  2791                                  		; AVL= Available to programmers	
  2792                                  
  2793                                  gdtd:
  2794 00006418 7700                            dw gdt_end - gdt - 1    ; Limit (size)
  2795 0000641A [A0630000]                      dd gdt			; Address of the GDT
  2796                                  
  2797                                  	; 20/08/2014
  2798                                  idtd:
  2799 0000641E 7F02                            dw idt_end - idt - 1    ; Limit (size)
  2800 00006420 [985B0100]                      dd idt			; Address of the IDT
  2801                                  
  2802                                  ; 20/02/2017
  2803                                  ;;; 11/03/2015
  2804                                  %include 'diskdata.s'	; DISK (BIOS) DATA (initialized)
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - diskdata.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 24/01/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; diskdata.inc (11/03/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - DISKDATA.INC
    20                              <1> ; Last Modification: 11/03/2015
    21                              <1> ;	(Initialized Disk Parameters Data section for 'DISKIO.INC') 
    22                              <1> ;
    23                              <1> 
    24                              <1> ;----------------------------------------
    25                              <1> ;	80286 INTERRUPT LOCATIONS	:
    26                              <1> ;	REFERENCED BY POST & BIOS	:
    27                              <1> ;----------------------------------------
    28                              <1> 
    29 00006424 [87640000]          <1> DISK_POINTER:	dd	MD_TBL6		; Pointer to Diskette Parameter Table
    30                              <1> 
    31                              <1> ; IBM PC-XT Model 286 source code ORGS.ASM (06/10/85) - 14/12/2014
    32                              <1> ;----------------------------------------------------------------
    33                              <1> ; DISK_BASE							:
    34                              <1> ;	THIS IS THE SET OF PARAMETERS REQUIRED FOR		:
    35                              <1> ;	DISKETTE OPERATION. THEY ARE POINTED AT BY THE		:
    36                              <1> ;	DATA VARIABLE @DISK_POINTER. TO MODIFY THE PARAMETERS,	:
    37                              <1> ;	BUILD ANOTHER PARAMETER BLOCK AND POINT AT IT		:
    38                              <1> ;----------------------------------------------------------------
    39                              <1> 
    40                              <1> ;DISK_BASE:	
    41                              <1> ;	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
    42                              <1> ;	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
    43                              <1> ;	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
    44                              <1> ;	DB	2		; 512 BYTES/SECTOR
    45                              <1> ;	;DB	15		; EOT (LAST SECTOR ON TRACK)
    46                              <1> ;	db	18		; (EOT for 1.44MB diskette)
    47                              <1> ;	DB	01BH		; GAP LENGTH
    48                              <1> ;	DB	0FFH		; DTL
    49                              <1> ;	;DB	054H		; GAP LENGTH FOR FORMAT
    50                              <1> ;	db	06ch		; (for 1.44MB dsikette)
    51                              <1> ;	DB	0F6H		; FILL BYTE FOR FORMAT
    52                              <1> ;	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
    53                              <1> ;	DB	8		; MOTOR START TIME (1/8 SECONDS)
    54                              <1> 
    55                              <1> ;----------------------------------------
    56                              <1> ;	ROM BIOS DATA AREAS		:
    57                              <1> ;----------------------------------------
    58                              <1> 
    59                              <1> ;DATA		SEGMENT AT 40H		; ADDRESS= 0040:0000
    60                              <1> 
    61                              <1> ;@EQUIP_FLAG	DW	?		; INSTALLED HARDWARE FLAGS
    62                              <1> 
    63                              <1> ;----------------------------------------
    64                              <1> ;	DISKETTE DATA AREAS		:
    65                              <1> ;----------------------------------------
    66                              <1> 
    67                              <1> ;@SEEK_STATUS	DB	?		; DRIVE RECALIBRATION STATUS
    68                              <1> ;					; BIT 3-0 = DRIVE 3-0 RECALIBRATION
    69                              <1> ;					; BEFORE NEXT SEEK IF BIT IS = 0
    70                              <1> ;@MOTOR_STATUS	DB	?		; MOTOR STATUS
    71                              <1> ;					; BIT 3-0 = DRIVE 3-0 CURRENTLY RUNNING
    72                              <1> ;					; BIT 7 = CURRENT OPERATION IS A WRITE
    73                              <1> ;@MOTOR_COUNT	DB	?		; TIME OUT COUNTER FOR MOTOR(S) TURN OFF
    74                              <1> ;@DSKETTE_STATUS DB	?		; RETURN CODE STATUS BYTE
    75                              <1> ;					; CMD_BLOCK  IN STACK FOR DISK OPERATION
    76                              <1> ;@NEC_STATUS	DB	7 DUP(?)	; STATUS BYTES FROM DISKETTE OPERATION
    77                              <1> 
    78                              <1> ;----------------------------------------
    79                              <1> ;	POST AND BIOS WORK DATA AREA	:
    80                              <1> ;----------------------------------------
    81                              <1> 
    82                              <1> ;@INTR_FLAG	DB	?		; FLAG INDICATING AN INTERRUPT HAPPENED
    83                              <1> 
    84                              <1> ;----------------------------------------
    85                              <1> ;	TIMER DATA AREA 		:
    86                              <1> ;----------------------------------------
    87                              <1> 
    88                              <1> ; 17/12/2014  (IRQ 0 - INT 08H)
    89                              <1> ;TIMER_LOW	equ	46Ch		; Timer ticks (counter)  @ 40h:006Ch
    90                              <1> ;TIMER_HIGH	equ	46Eh		; (18.2 timer ticks per second)
    91                              <1> ;TIMER_OFL	equ	470h		; Timer - 24 hours flag  @ 40h:0070h
    92                              <1> 
    93                              <1> ;----------------------------------------
    94                              <1> ;	ADDITIONAL MEDIA DATA		:
    95                              <1> ;----------------------------------------
    96                              <1> 
    97                              <1> ;@LASTRATE	DB	?		; LAST DISKETTE DATA RATE SELECTED
    98                              <1> ;@DSK_STATE	DB	?		; DRIVE 0 MEDIA STATE
    99                              <1> ;		DB	?		; DRIVE 1 MEDIA STATE
   100                              <1> ;		DB	?		; DRIVE 0 OPERATION START STATE
   101                              <1> ;		DB	?		; DRIVE 1 OPERATION START STATE
   102                              <1> ;@DSK_TRK	DB	?		; DRIVE 0 PRESENT CYLINDER
   103                              <1> ;		DB	?		; DRIVE 1 PRESENT CYLINDER
   104                              <1> 
   105                              <1> ;DATA		ENDS			; END OF BIOS DATA SEGMENT
   106                              <1> 
   107                              <1> ;--------------------------------------------------------
   108                              <1> ;	DRIVE TYPE TABLE				:
   109                              <1> ;--------------------------------------------------------
   110                              <1> 		; 16/02/2015 (unix386.s, 32 bit modifications)
   111                              <1> DR_TYPE:
   112 00006428 01                  <1> 		DB	01		;DRIVE TYPE, MEDIA TABLE
   113                              <1>                 ;DW      MD_TBL1
   114 00006429 [46640000]          <1> 		dd	MD_TBL1
   115 0000642D 82                  <1> 		DB	02+BIT7ON
   116                              <1> 		;DW      MD_TBL2
   117 0000642E [53640000]          <1>                 dd      MD_TBL2
   118 00006432 02                  <1> DR_DEFAULT:	DB	02
   119                              <1>                 ;DW      MD_TBL3
   120 00006433 [60640000]          <1> 		dd      MD_TBL3
   121 00006437 03                  <1> 		DB	03
   122                              <1>                 ;DW      MD_TBL4
   123 00006438 [6D640000]          <1> 		dd      MD_TBL4
   124 0000643C 84                  <1> 		DB	04+BIT7ON
   125                              <1>                 ;DW      MD_TBL5
   126 0000643D [7A640000]          <1> 		dd      MD_TBL5
   127 00006441 04                  <1> 		DB	04
   128                              <1>                 ;DW      MD_TBL6
   129 00006442 [87640000]          <1> 		dd      MD_TBL6
   130                              <1> DR_TYPE_E       equ $                   ; END OF TABLE
   131                              <1> ;DR_CNT		EQU	(DR_TYPE_E-DR_TYPE)/3
   132                              <1> DR_CNT		equ	(DR_TYPE_E-DR_TYPE)/5
   133                              <1> ;--------------------------------------------------------
   134                              <1> ;	MEDIA/DRIVE PARAMETER TABLES			:
   135                              <1> ;--------------------------------------------------------
   136                              <1> ;--------------------------------------------------------
   137                              <1> ;	360 KB MEDIA IN 360 KB DRIVE			:
   138                              <1> ;--------------------------------------------------------
   139                              <1> MD_TBL1:        
   140 00006446 DF                  <1> 	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   141 00006447 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   142 00006448 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   143 00006449 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   144 0000644A 09                  <1> 	DB	09		; EOT (LAST SECTOR ON TRACK)
   145 0000644B 2A                  <1> 	DB	02AH		; GAP LENGTH
   146 0000644C FF                  <1> 	DB	0FFH		; DTL
   147 0000644D 50                  <1> 	DB	050H		; GAP LENGTH FOR FORMAT
   148 0000644E F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   149 0000644F 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   150 00006450 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   151 00006451 27                  <1> 	DB	39		; MAX. TRACK NUMBER
   152 00006452 80                  <1> 	DB	RATE_250	; DATA TRANSFER RATE
   153                              <1> ;--------------------------------------------------------
   154                              <1> ;	360 KB MEDIA IN 1.2 MB DRIVE			:
   155                              <1> ;--------------------------------------------------------
   156                              <1> MD_TBL2:        
   157 00006453 DF                  <1> 	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   158 00006454 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   159 00006455 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   160 00006456 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   161 00006457 09                  <1> 	DB	09		; EOT (LAST SECTOR ON TRACK)
   162 00006458 2A                  <1> 	DB	02AH		; GAP LENGTH
   163 00006459 FF                  <1> 	DB	0FFH		; DTL
   164 0000645A 50                  <1> 	DB	050H		; GAP LENGTH FOR FORMAT
   165 0000645B F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   166 0000645C 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   167 0000645D 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   168 0000645E 27                  <1> 	DB	39		; MAX. TRACK NUMBER
   169 0000645F 40                  <1> 	DB	RATE_300	; DATA TRANSFER RATE
   170                              <1> ;--------------------------------------------------------
   171                              <1> ;	1.2 MB MEDIA IN 1.2 MB DRIVE			:
   172                              <1> ;--------------------------------------------------------
   173                              <1> MD_TBL3:
   174 00006460 DF                  <1> 	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   175 00006461 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   176 00006462 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   177 00006463 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   178 00006464 0F                  <1> 	DB	15		; EOT (LAST SECTOR ON TRACK)
   179 00006465 1B                  <1> 	DB	01BH		; GAP LENGTH
   180 00006466 FF                  <1> 	DB	0FFH		; DTL
   181 00006467 54                  <1> 	DB	054H		; GAP LENGTH FOR FORMAT
   182 00006468 F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   183 00006469 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   184 0000646A 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   185 0000646B 4F                  <1> 	DB	79		; MAX. TRACK NUMBER
   186 0000646C 00                  <1> 	DB	RATE_500	; DATA TRANSFER RATE
   187                              <1> ;--------------------------------------------------------
   188                              <1> ;	720 KB MEDIA IN 720 KB DRIVE			:
   189                              <1> ;--------------------------------------------------------
   190                              <1> MD_TBL4:
   191 0000646D DF                  <1> 	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   192 0000646E 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   193 0000646F 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   194 00006470 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   195 00006471 09                  <1> 	DB	09		; EOT (LAST SECTOR ON TRACK)
   196 00006472 2A                  <1> 	DB	02AH		; GAP LENGTH
   197 00006473 FF                  <1> 	DB	0FFH		; DTL
   198 00006474 50                  <1> 	DB	050H		; GAP LENGTH FOR FORMAT
   199 00006475 F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   200 00006476 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   201 00006477 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   202 00006478 4F                  <1> 	DB	79		; MAX. TRACK NUMBER
   203 00006479 80                  <1> 	DB	RATE_250	; DATA TRANSFER RATE
   204                              <1> ;--------------------------------------------------------
   205                              <1> ;	720 KB MEDIA IN 1.44 MB DRIVE			:
   206                              <1> ;--------------------------------------------------------
   207                              <1> MD_TBL5:
   208 0000647A DF                  <1> 	DB	11011111B	; SRT=D, HD UNLOAD=0F - 1ST SPECIFY BYTE
   209 0000647B 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   210 0000647C 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   211 0000647D 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   212 0000647E 09                  <1> 	DB	09		; EOT (LAST SECTOR ON TRACK)
   213 0000647F 2A                  <1> 	DB	02AH		; GAP LENGTH
   214 00006480 FF                  <1> 	DB	0FFH		; DTL
   215 00006481 50                  <1> 	DB	050H		; GAP LENGTH FOR FORMAT
   216 00006482 F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   217 00006483 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   218 00006484 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   219 00006485 4F                  <1> 	DB	79		; MAX. TRACK NUMBER
   220 00006486 80                  <1> 	DB	RATE_250	; DATA TRANSFER RATE
   221                              <1> ;--------------------------------------------------------
   222                              <1> ;	1.44 MB MEDIA IN 1.44 MB DRIVE			:
   223                              <1> ;--------------------------------------------------------
   224                              <1> MD_TBL6:
   225 00006487 AF                  <1> 	DB	10101111B	; SRT=A, HD UNLOAD=0F - 1ST SPECIFY BYTE
   226 00006488 02                  <1> 	DB	2		; HD LOAD=1, MODE=DMA - 2ND SPECIFY BYTE
   227 00006489 25                  <1> 	DB	MOTOR_WAIT	; WAIT TIME AFTER OPERATION TILL MOTOR OFF
   228 0000648A 02                  <1> 	DB	2		; 512 BYTES/SECTOR
   229 0000648B 12                  <1> 	DB	18		; EOT (LAST SECTOR ON TRACK)
   230 0000648C 1B                  <1> 	DB	01BH		; GAP LENGTH
   231 0000648D FF                  <1> 	DB	0FFH		; DTL
   232 0000648E 6C                  <1> 	DB	06CH		; GAP LENGTH FOR FORMAT
   233 0000648F F6                  <1> 	DB	0F6H		; FILL BYTE FOR FORMAT
   234 00006490 0F                  <1> 	DB	15		; HEAD SETTLE TIME (MILLISECONDS)
   235 00006491 08                  <1> 	DB	8		; MOTOR START TIME (1/8 SECONDS)
   236 00006492 4F                  <1> 	DB	79		; MAX. TRACK NUMBER
   237 00006493 00                  <1> 	DB	RATE_500	; DATA TRANSFER RATE
   238                              <1> 
   239                              <1> 
   240                              <1> ; << diskette.inc >>
   241                              <1> ; +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
   242                              <1> ;
   243                              <1> ;----------------------------------------
   244                              <1> ;	ROM BIOS DATA AREAS		:
   245                              <1> ;----------------------------------------
   246                              <1> 
   247                              <1> ;DATA		SEGMENT AT 40H		; ADDRESS= 0040:0000
   248                              <1> 
   249                              <1> ;----------------------------------------
   250                              <1> ;	FIXED DISK DATA AREAS		:
   251                              <1> ;----------------------------------------
   252                              <1> 
   253                              <1> ;DISK_STATUS1:	DB	0		; FIXED DISK STATUS
   254                              <1> ;HF_NUM:		DB	0		; COUNT OF FIXED DISK DRIVES
   255                              <1> ;CONTROL_BYTE:	DB	0		; HEAD CONTROL BYTE
   256                              <1> ;@PORT_OFF	DB	?		;  RESERVED (PORT OFFSET)
   257                              <1> 
   258                              <1> ;----------------------------------------
   259                              <1> ;	ADDITIONAL MEDIA DATA		:
   260                              <1> ;----------------------------------------
   261                              <1> 
   262                              <1> ;@LASTRATE	DB	?		; LAST DISKETTE DATA RATE SELECTED
   263                              <1> ;HF_STATUS	DB	0		; STATUS REGISTER
   264                              <1> ;HF_ERROR	DB	0		; ERROR REGISTER
   265                              <1> ;HF_INT_FLAG	DB	0		; FIXED DISK INTERRUPT FLAG
   266                              <1> ;HF_CNTRL	DB	0		; COMBO FIXED DISK/DISKETTE CARD BIT 0=1
   267                              <1> ;@DSK_STATE	DB	?		; DRIVE 0 MEDIA STATE
   268                              <1> ;		DB	?		; DRIVE 1 MEDIA STATE
   269                              <1> ;		DB	?		; DRIVE 0 OPERATION START STATE
   270                              <1> ;		DB	?		; DRIVE 1 OPERATION START STATE
   271                              <1> ;@DSK_TRK	DB	?		; DRIVE 0 PRESENT CYLINDER
   272                              <1> ;		DB	?		; DRIVE 1 PRESENT CYLINDER
   273                              <1> 
   274                              <1> ;DATA		ENDS			; END OF BIOS DATA SEGMENT
   275                              <1> ;
   276                              <1> ; +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
   277                              <1> 
   278                              <1> ERR_TBL:
   279 00006494 E0                  <1> 	db	NO_ERR
   280 00006495 024001BB            <1> 	db	BAD_ADDR_MARK,BAD_SEEK,BAD_CMD,UNDEF_ERR
   281 00006499 04BB100A            <1> 	db	RECORD_NOT_FND,UNDEF_ERR,BAD_ECC,BAD_SECTOR
   282                              <1> 
   283                              <1> ; 17/12/2014 (mov ax, [cfd])
   284                              <1> ; 11/12/2014
   285 0000649D 00                  <1> cfd:		db 0			; current floppy drive (for GET_PARM)
   286                              <1> ; 17/12/2014				; instead of 'DISK_POINTER'
   287 0000649E 01                  <1> pfd:		db 1			; previous floppy drive (for GET_PARM)
   288                              <1> 					; (initial value of 'pfd 
   289                              <1> 					; must be different then 'cfd' value
   290                              <1> 					; to force updating/initializing
   291                              <1> 					; current drive parameters) 
   292 0000649F 90                  <1> align 2
   293                              <1> 
   294 000064A0 F001                <1> HF_PORT:	dw 	1F0h  ; Default = 1F0h
   295                              <1> 			      ; (170h)
   296 000064A2 F603                <1> HF_REG_PORT:	dw	3F6h  ; HF_PORT + 206h
   297                              <1> 
   298                              <1> ; 05/01/2015 
   299 000064A4 00                  <1> hf_m_s:         db      0     ; (0 = Master, 1 = Slave)
   300                              <1> 
   301                              <1> ; *****************************************************************************
  2805                                  
  2806 000064A5 90                      Align 2
  2807                                  
  2808                                  ; 04/11/2014 (Retro UNIX 386 v1)
  2809 000064A6 0000                    mem_1m_1k:   dw 0  ; Number of contiguous KB between
  2810                                                       ; 1 and 16 MB, max. 3C00h = 15 MB.
  2811 000064A8 0000                    mem_16m_64k: dw 0  ; Number of contiguous 64 KB blocks
  2812                                  		   ; between 16 MB and 4 GB.
  2813                                  
  2814                                  ; 12/11/2014 (Retro UNIX 386 v1)
  2815 000064AA 00                      boot_drv:    db 0 ; boot drive number (physical)
  2816                                  ; 24/11/2014
  2817 000064AB 00                      drv:	     db 0 
  2818 000064AC 00                      last_drv:    db 0 ; last hdd
  2819 000064AD 00                      hdc:         db 0  ; number of hard disk drives
  2820                                  		     ; (present/detected)
  2821                                  
  2822                                  ; 24/11/2014 (Retro UNIX 386 v1)
  2823                                  ; Physical drive type & flags
  2824 000064AE 00                      fd0_type:    db 0  ; floppy drive type
  2825 000064AF 00                      fd1_type:    db 0  ; 4 = 1.44 Mb, 80 track, 3.5" (18 spt)
  2826                                  		     ; 6 = 2.88 Mb, 80 track, 3.5" (36 spt)
  2827                                  		     ; 3 = 720 Kb, 80 track, 3.5" (9 spt)
  2828                                  		     ; 2 = 1.2 Mb, 80 track, 5.25" (15 spt)
  2829                                  		     ; 1 = 360 Kb, 40 track, 5.25" (9 spt)		
  2830 000064B0 00                      hd0_type:    db 0  ; EDD status for hd0 (bit 7 = present flag)
  2831 000064B1 00                      hd1_type:    db 0  ; EDD status for hd1 (bit 7 = present flag)
  2832 000064B2 00                      hd2_type:    db 0  ; EDD status for hd2 (bit 7 = present flag)
  2833 000064B3 00                      hd3_type:    db 0  ; EDD status for hd3 (bit 7 = present flag)
  2834                                  		     ; bit 0 - Fixed disk access subset supported
  2835                                  		     ; bit 1 - Drive locking and ejecting
  2836                                  		     ; bit 2 - Enhanced disk drive support
  2837                                  		     ; bit 3 = Reserved (64 bit EDD support)
  2838                                  		     ; (If bit 0 is '1' Retro UNIX 386 v1
  2839                                  		     ; will interpret it as 'LBA ready'!)
  2840                                  
  2841                                  ; 11/03/2015 - 10/07/2015
  2842 000064B4 000000000000000000-     drv.cylinders: dw 0,0,0,0,0,0,0
  2842 000064BD 0000000000         
  2843 000064C2 000000000000000000-     drv.heads:     dw 0,0,0,0,0,0,0
  2843 000064CB 0000000000         
  2844 000064D0 000000000000000000-     drv.spt:       dw 0,0,0,0,0,0,0
  2844 000064D9 0000000000         
  2845 000064DE 000000000000000000-     drv.size:      dd 0,0,0,0,0,0,0
  2845 000064E7 000000000000000000-
  2845 000064F0 000000000000000000-
  2845 000064F9 00                 
  2846 000064FA 00000000000000          drv.status:    db 0,0,0,0,0,0,0
  2847 00006501 00000000000000          drv.error:     db 0,0,0,0,0,0,0	
  2848                                  
  2849                                  Align 2
  2850                                  
  2851                                  ;;; 11/03/2015
  2852                                  %include 'kybdata.s'	; KEYBOARD (BIOS) DATA
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - kybdata.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 17/01/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 17/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; kybdata.inc (11/03/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - KYBDATA.INC
    20                              <1> ; Last Modification: 11/03/2015
    21                              <1> ;		 (Data Section for 'KEYBOARD.INC')	
    22                              <1> ;
    23                              <1> ; ///////// KEYBOARD DATA ///////////////
    24                              <1> 
    25                              <1> ; 05/12/2014
    26                              <1> ; 04/12/2014 (derived from pc-xt-286 bios source code -1986-) 
    27                              <1> ; 03/06/86  KEYBOARD BIOS
    28                              <1> 
    29                              <1> ;---------------------------------------------------------------------------------
    30                              <1> ;	KEY IDENTIFICATION SCAN TABLES
    31                              <1> ;---------------------------------------------------------------------------------
    32                              <1> 
    33                              <1> ;-----	TABLES FOR ALT CASE ------------
    34                              <1> ;-----	ALT-INPUT-TABLE 
    35 00006508 524F50514B          <1> K30:	db	82,79,80,81,75
    36 0000650D 4C4D474849          <1> 	db	76,77,71,72,73		; 10 NUMBER ON KEYPAD
    37                              <1> ;-----	SUPER-SHIFT-TABLE 
    38 00006512 101112131415        <1> 	db	16,17,18,19,20,21	; A-Z TYPEWRITER CHARS
    39 00006518 161718191E1F        <1> 	db	22,23,24,25,30,31
    40 0000651E 202122232425        <1> 	db	32,33,34,35,36,37
    41 00006524 262C2D2E2F30        <1> 	db	38,44,45,46,47,48
    42 0000652A 3132                <1> 	db	49,50
    43                              <1> 
    44                              <1> ;-----	TABLE OF SHIFT KEYS AND MASK VALUES
    45                              <1> ;-----	KEY_TABLE 
    46 0000652C 52                  <1> _K6:    db      INS_KEY                 ; INSERT KEY
    47 0000652D 3A4546381D          <1> 	db	CAPS_KEY,NUM_KEY,SCROLL_KEY,ALT_KEY,CTL_KEY
    48 00006532 2A36                <1>         db      LEFT_KEY,RIGHT_KEY
    49                              <1> _K6L    equ     $-_K6
    50                              <1> 
    51                              <1> ;-----	MASK_TABLE
    52 00006534 80                  <1> _K7:    db      INS_SHIFT               ; INSERT MODE SHIFT
    53 00006535 4020100804          <1> 	db	CAPS_SHIFT,NUM_SHIFT,SCROLL_SHIFT,ALT_SHIFT,CTL_SHIFT
    54 0000653A 0201                <1> 	db	LEFT_SHIFT,RIGHT_SHIFT
    55                              <1> 
    56                              <1> ;-----	TABLES FOR CTRL CASE		;---- CHARACTERS ------
    57 0000653C 1BFF00FFFFFF        <1> _K8:	db	27,-1,0,-1,-1,-1	; Esc, 1, 2, 3, 4, 5
    58 00006542 1EFFFFFFFF1F        <1> 	db 	30,-1,-1,-1,-1,31	; 6, 7, 8, 9, 0, -
    59 00006548 FF7FFF111705        <1> 	db	-1,127,-1,17,23,5	; =, Bksp, Tab, Q, W, E
    60 0000654E 12141915090F        <1> 	db	18,20,25,21,9,15	; R, T, Y, U, I, O
    61 00006554 101B1D0AFF01        <1> 	db	16,27,29,10,-1,1	; P, [, ], Enter, Ctrl, A
    62 0000655A 13040607080A        <1> 	db	19,4,6,7,8,10		; S, D, F, G, H, J
    63 00006560 0B0CFFFFFFFF        <1> 	db	11,12,-1,-1,-1,-1	; K, L, :, ', `, LShift
    64 00006566 1C1A18031602        <1> 	db	28,26,24,3,22,2		; Bkslash, Z, X, C, V, B
    65 0000656C 0E0DFFFFFFFF        <1> 	db	14,13,-1,-1,-1,-1	; N, M, ,, ., /, RShift
    66 00006572 96FF20FF            <1> 	db	150,-1,' ',-1		; *, ALT, Spc, CL
    67                              <1> 	;				;----- FUNCTIONS ------		
    68 00006576 5E5F60616263        <1> 	db 	94,95,96,97,98,99	; F1 - F6
    69 0000657C 64656667FFFF        <1> 	db	100,101,102,103,-1,-1	; F7 - F10, NL, SL
    70 00006582 778D848E738F        <1> 	db	119,141,132,142,115,143	; Home, Up, PgUp, -, Left, Pad5
    71 00006588 749075917692        <1> 	db 	116,144,117,145,118,146 ; Right, +, End, Down, PgDn, Ins
    72 0000658E 93FFFFFF898A        <1> 	db	147,-1,-1,-1,137,138	; Del, SysReq, Undef, WT, F11, F12
    73                              <1> 
    74                              <1> ;-----	TABLES FOR LOWER CASE ----------
    75 00006594 1B3132333435363738- <1> K10:	db 	27,'1234567890-=',8,9
    75 0000659D 39302D3D0809        <1>
    76 000065A3 71776572747975696F- <1> 	db 	'qwertyuiop[]',13,-1,'asdfghjkl;',39
    76 000065AC 705B5D0DFF61736466- <1>
    76 000065B5 67686A6B6C3B27      <1>
    77 000065BC 60FF5C7A786376626E- <1> 	db	96,-1,92,'zxcvbnm,./',-1,'*',-1,' ',-1
    77 000065C5 6D2C2E2FFF2AFF20FF  <1>
    78                              <1> ;-----	LC TABLE SCAN
    79 000065CE 3B3C3D3E3F          <1> 	db	59,60,61,62,63		; BASE STATE OF F1 - F10
    80 000065D3 4041424344          <1> 	db	64,65,66,67,68
    81 000065D8 FFFF                <1> 	db	-1,-1			; NL, SL
    82                              <1> 
    83                              <1> ;-----	KEYPAD TABLE
    84 000065DA 474849FF4BFF        <1> K15:	db	71,72,73,-1,75,-1	; BASE STATE OF KEYPAD KEYS
    85 000065E0 4DFF4F50515253      <1> 	db	77,-1,79,80,81,82,83
    86 000065E7 FFFF5C8586          <1> 	db	-1,-1,92,133,134	; SysRq, Undef, WT, F11, F12
    87                              <1> 
    88                              <1> ;-----	TABLES FOR UPPER CASE ----------
    89 000065EC 1B21402324255E262A- <1> K11:	db 	27,'!@#$%',94,'&*()_+',8,0
    89 000065F5 28295F2B0800        <1>
    90 000065FB 51574552545955494F- <1> 	db 	'QWERTYUIOP{}',13,-1,'ASDFGHJKL:"'
    90 00006604 507B7D0DFF41534446- <1>
    90 0000660D 47484A4B4C3A22      <1>
    91 00006614 7EFF7C5A584356424E- <1> 	db	126,-1,'|ZXCVBNM<>?',-1,'*',-1,' ',-1
    91 0000661D 4D3C3E3FFF2AFF20FF  <1>
    92                              <1> ;-----	UC TABLE SCAN
    93 00006626 5455565758          <1> K12:	db	84,85,86,87,88		; SHIFTED STATE OF F1 - F10
    94 0000662B 595A5B5C5D          <1> 	db	89,90,91,92,93
    95 00006630 FFFF                <1> 	db	-1,-1			; NL, SL
    96                              <1> 
    97                              <1> ;-----	NUM STATE TABLE
    98 00006632 3738392D3435362B31- <1> K14:	db 	'789-456+1230.'		; NUMLOCK STATE OF KEYPAD KEYS
    98 0000663B 3233302E            <1>
    99                              <1> 	;
   100 0000663F FFFF7C8788          <1> 	db	-1,-1,124,135,136	; SysRq, Undef, WT, F11, F12
   101                              <1> 
   102                              <1> ; 26/08/2014
   103                              <1> ; Retro UNIX 8086 v1 - UNIX.ASM (03/03/2014)
   104                              <1> ; Derived from IBM "pc-at" 
   105                              <1> ; rombios source code (06/10/1985)
   106                              <1> ; 'dseg.inc'
   107                              <1> 
   108                              <1> ;---------------------------------------;
   109                              <1> ;	SYSTEM DATA AREA		;
   110                              <1> ;----------------------------------------
   111 00006644 00                  <1> BIOS_BREAK	db	0		; BIT 7=1 IF BREAK KEY HAS BEEN PRESSED
   112                              <1> 
   113                              <1> ;----------------------------------------
   114                              <1> ;	KEYBOARD DATA AREAS		;
   115                              <1> ;----------------------------------------
   116                              <1> 
   117 00006645 00                  <1> KB_FLAG		db	0		; KEYBOARD SHIFT STATE AND STATUS FLAGS
   118 00006646 00                  <1> KB_FLAG_1	db	0		; SECOND BYTE OF KEYBOARD STATUS
   119 00006647 00                  <1> KB_FLAG_2	db	0		; KEYBOARD LED FLAGS
   120 00006648 00                  <1> KB_FLAG_3	db	0		; KEYBOARD MODE STATE AND TYPE FLAGS
   121 00006649 00                  <1> ALT_INPUT	db	0		; STORAGE FOR ALTERNATE KEY PAD ENTRY
   122 0000664A [5A660000]          <1> BUFFER_START	dd	KB_BUFFER 	; OFFSET OF KEYBOARD BUFFER START
   123 0000664E [7A660000]          <1> BUFFER_END	dd	KB_BUFFER + 32	; OFFSET OF END OF BUFFER
   124 00006652 [5A660000]          <1> BUFFER_HEAD	dd	KB_BUFFER 	; POINTER TO HEAD OF KEYBOARD BUFFER
   125 00006656 [5A660000]          <1> BUFFER_TAIL	dd	KB_BUFFER 	; POINTER TO TAIL OF KEYBOARD BUFFER
   126                              <1> ; ------	HEAD = TAIL	INDICATES THAT THE BUFFER IS EMPTY
   127 0000665A 0000<rept>          <1> KB_BUFFER	times	16 dw 0		; ROOM FOR 16 SCAN CODE ENTRIES
   128                              <1> 
   129                              <1> ; /// End Of KEYBOARD DATA ///
  2853                                  %include 'vidata.s'	; VIDEO (BIOS) DATA
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.3 - vidata.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 24/11/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 16/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.15 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; vidata.inc (11/03/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-AT' BIOS source code (1985) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - VIDATA.S
    20                              <1> ; Last Modification: 11/03/2015
    21                              <1> ;		    (Data section for 'VIDEO.INC')	
    22                              <1> ;
    23                              <1> ; ///////// VIDEO DATA ///////////////
    24                              <1> 
    25                              <1> ;----------------------------------------
    26                              <1> ;	VIDEO DISPLAY DATA AREA		;
    27                              <1> ;----------------------------------------
    28 0000667A 03                  <1> CRT_MODE:	db	3	; CURRENT DISPLAY MODE (TYPE)
    29 0000667B 29                  <1> CRT_MODE_SET:	db	29h	; CURRENT SETTING OF THE 3X8 REGISTER
    30                              <1> 				; (29h default setting for video mode 3)
    31                              <1> 				; Mode Select register Bits
    32                              <1> 				;   BIT 0 - 80x25 (1), 40x25 (0)
    33                              <1> 				;   BIT 1 - ALPHA (0), 320x200 GRAPHICS (1)
    34                              <1> 				;   BIT 2 - COLOR (0), BW (1)
    35                              <1> 				;   BIT 3 - Video Sig. ENABLE (1), DISABLE (0)
    36                              <1> 				;   BIT 4 - 640x200 B&W Graphics Mode (1)
    37                              <1> 				;   BIT 5 - ALPHA mode BLINKING (1)
    38                              <1> 				;   BIT 6, 7 - Not Used
    39                              <1> 
    40                              <1> ; Mode 0 - 2Ch = 101100b	; 40x25 text, 16 gray colors
    41                              <1> ; Mode 1 - 28h = 101000b	; 40x25 text, 16 fore colors, 8 back colors
    42                              <1> ; Mode 2 - 2Dh = 101101b	; 80x25 text, 16 gray colors	
    43                              <1> ; Mode 3 - 29h = 101001b	; 80x25 text, 16 fore color, 8 back color
    44                              <1> ; Mode 4 - 2Ah = 101010b	; 320x200 graphics, 4 colors
    45                              <1> ; Mode 5 - 2Eh = 101110b	; 320x200 graphics, 4 gray colors
    46                              <1> ; Mode 6 - 1Eh = 011110b	; 640x200 graphics, 2 colors
    47                              <1> ; Mode 7 - 29h = 101001b	; 80x25 text, black & white colors
    48                              <1> ; Mode & 37h = Video signal OFF
    49                              <1> 
    50                              <1> ; 24/06/2016
    51 0000667C 50                  <1> CRT_COLS:	db	80	; Number of columns
    52                              <1> 
    53                              <1> ; 01/07/2016
    54 0000667D 00                  <1> CRT_PALETTE:	db 	0	; Current palette setting
    55                              <1> 
    56                              <1> ; 03/07/2016
    57 0000667E 10                  <1> CHAR_HEIGHT:	db	16	; Default character height
    58 0000667F 60                  <1> VGA_VIDEO_CTL:	db	60h	; ROM BIOS DATA AREA Offset 87h
    59 00006680 F9                  <1> VGA_SWITCHES:	db 	0F9h	; Feature Bit Switches (the basic screen)
    60 00006681 51                  <1> VGA_MODESET_CTL: db	051h	; Basic mode set options (VGA video flags)
    61                              <1> 				; ROM BIOS DATA AREA Offset 89h
    62                              <1> 				; Bit 7, 4 : Mode
    63                              <1> 				;	  01 : 400-line mode
    64                              <1> 				; Bit 6	: Display switch enabled = 1			
    65                              <1> 				; Bit 5	: Reserved = 0
    66                              <1> 				; Bit 3	: Default palette loading 
    67                              <1> 				;	  disabled = 0
    68                              <1> 				; Bit 2 : Color monitor = 0
    69                              <1> 				; Bit 1 = Gray scale summing 
    70                              <1> 				;	  disabled = 0
    71                              <1> 				; Bit 0 = VGA active = 1
    72 00006682 19                  <1> VGA_ROWS:	db	25
    73                              <1> 
    74                              <1> ; 16/01/2016
    75                              <1> chr_attrib:  ; Character color/attributes for viode pages (0 to 7)
    76 00006683 0707070707070707    <1> 	db	07h, 07h, 07h, 07h, 07h, 07h, 07h, 07h
    77                              <1> ; 30/01/2016
    78                              <1> vmode:
    79 0000668B 0303030303030303    <1> 	db	3,3,3,3,3,3,3,3 ; video modes for pseudo screens 
    80                              <1> 
    81                              <1> CURSOR_MODE: ; cursor start (ch) = 14, cursor end (cl) = 15
    82 00006693 0F0E                <1> 	db	15, 14 ; 07/07/2016 - TRDOS 386 (TRDOS v2.0)
    83                              <1> 
    84                              <1> ;align 4
    85                              <1> ;VGA_BASE: ; 26/07/2016
    86                              <1> ;	dd	 0B8000h  ; (Mode < 0Dh) or 0A0000h (mode >= 0Dh)
    87                              <1> 
    88 00006695 90                  <1> align 2
    89                              <1> 
    90                              <1> vga_modes:
    91                              <1> 	; 25/07/2016
    92                              <1> 	; 09/07/2016
    93                              <1> 	; 03/07/2016
    94                              <1> 	; valid (implemented) video modes (>7, extension to IBM PC CGA modes)
    95 00006696 0302010007040506    <1> 	db 	03h, 02h, 01h, 00h, 07h, 04h, 05h, 06h
    96                              <1> vga_g_modes: ; 31/07/2016
    97 0000669E 13F0126A0D0E1011    <1> 	db	13h, 0F0h, 12h, 6Ah, 0Dh, 0Eh, 10h, 11h
    98                              <1> vga_mode_count equ $ - vga_modes
    99                              <1> vga_g_mode_count equ $ - vga_g_modes
   100                              <1> 
   101                              <1> vga_mode_tbl_ptr:
   102                              <1> 	; 25/07/2016
   103 000066A6 [06670000]          <1> 	dd	vga_mode_03h
   104 000066AA [06670000]          <1> 	dd	vga_mode_03h ; mode 02h -> mode 03h 
   105 000066AE [46670000]          <1> 	dd	vga_mode_01h
   106 000066B2 [46670000]          <1> 	dd	vga_mode_01h ; mode 00h -> mode 01h
   107                              <1> 	;dd	vga_mode_07h
   108 000066B6 [06670000]          <1> 	dd	vga_mode_03h ; mode 07h -> mode 03h
   109 000066BA [86670000]          <1> 	dd	vga_mode_04h
   110 000066BE [86670000]          <1> 	dd	vga_mode_04h ; mode 05h -> mode 04h	
   111 000066C2 [C6670000]          <1> 	dd	vga_mode_06h
   112 000066C6 [06680000]          <1> 	dd	vga_mode_13h
   113 000066CA [46680000]          <1> 	dd	vga_mode_F0h
   114 000066CE [86680000]          <1> 	dd	vga_mode_12h
   115 000066D2 [C6680000]          <1> 	dd	vga_mode_6Ah
   116 000066D6 [06690000]          <1> 	dd	vga_mode_0Dh
   117 000066DA [46690000]          <1> 	dd	vga_mode_0Eh
   118 000066DE [86690000]          <1> 	dd	vga_mode_10h
   119 000066E2 [C6690000]          <1> 	dd	vga_mode_11h	
   120                              <1> 
   121                              <1> vga_memmodel: 
   122                              <1> 	; 25/07/2016
   123                              <1> 	; 07/07/2016
   124                              <1> 	CTEXT	equ 0
   125                              <1> 	;MTEXT	equ 1
   126                              <1> 	MTEXT	equ 0 ; mode 07h -> mode 03h
   127                              <1> 	CGA	equ 2
   128                              <1> 	LINEAR8 equ 5
   129                              <1> 	PLANAR4	equ 4
   130                              <1> 	PLANAR1	equ 3
   131 000066E6 0000000000020202    <1> 	db	CTEXT, CTEXT, CTEXT, CTEXT, MTEXT, CGA, CGA, CGA
   132                              <1> vga_g_memmodel: ; 31/07/2016
   133 000066EE 0504040404040403    <1> 	db	LINEAR8, PLANAR4, PLANAR4, PLANAR4, PLANAR4, PLANAR4, PLANAR4, PLANAR1
   134                              <1> ;vga_pixbits:
   135                              <1> ;	; 25/07/2016
   136                              <1> ;	; 08/07/2016
   137                              <1> ;	db 	4, 4, 4, 4, 4, 2, 2, 1, 8, 4, 4, 4, 4, 4, 4, 1
   138                              <1> vga_dac_s:
   139 000066F6 020202020001010103- <1> 	db	2, 2, 2, 2, 0, 1, 1, 1, 3, 3, 2, 2, 1, 1, 2, 2  
   139 000066FF 03020201010202      <1>
   140                              <1> 						; (vgatables.h, VGAMODES, dac) 
   141                              <1> 						; 17/11/2020
   142                              <1> vga_params:
   143                              <1> 	; 23/11/2020
   144                              <1> 	; 16/11/2020
   145                              <1> 	; 09/11/2020, 10/11/2020, 11/11/2020 (TRDOS 386 v2.0.3)
   146                              <1> 	; 25/07/2016 
   147                              <1> 	; 19/07/2016
   148                              <1> 	; 03/07/2016
   149                              <1> 	; derived from 'Plex86/Bochs VGABios' source code
   150                              <1> 	; vgabios-0.7a (2011)
   151                              <1> 	; by the LGPL VGABios Developers Team (2001-2008)
   152                              <1> 	; 'vgatables.h'
   153                              <1> 	; Oracle VirtualBox 5.0.24 VGABios Source Code
   154                              <1> 	; ('vgabios.c', 'vgatables.h', 'vgafonts.h', 'vgarom.asm')
   155                              <1> 
   156                              <1> 	; 09/11/2020
   157                              <1> 	; Block Structure of Video Parameter Table
   158                              <1> 	;
   159                              <1> 	; Offset	# Bytes		Contents
   160                              <1> 	;
   161                              <1> 	;  0		1		# columns
   162                              <1> 	;  1		1  		# rows - 1 
   163                              <1> 	;  2		1		Pixels/character
   164                              <1> 	;  3-4		2		Page length		
   165                              <1> 	;  5-8		4		Sequencer Registers
   166                              <1> 	;  9		1		Miscellaneous Register	
   167                              <1> 	;  10-34	25		CRTC Registers
   168                              <1> 	;  35-54	20		Attribute Registers
   169                              <1> 	;  55-63	9		Graphics Controller Registers
   170                              <1> 	;
   171                              <1> 	; Ref: Programmer's Guide to EGA, VGA, and Super VGA cards
   172                              <1> 	; (Richard F. Ferraro, 1994)  
   173                              <1> 
   174                              <1> 	;
   175                              <1> vga_mode_03h:  ; mode 03h, 80*25 text, CGA colors
   176                              <1> 	; 11/11/2020
   177 00006706 5018100010          <1>  	db	80, 24, 16, 00h, 10h ; tw, th-1, ch, slength (5)
   178 0000670B 00030002            <1>  	db	00h, 03h, 00h, 02h ; sequ regs (4)
   179 0000670F 67                  <1>  	db	67h	; misc reg (1)
   180 00006710 5F4F50825581BF1F    <1>  	db	5Fh, 4Fh, 50h, 82h, 55h, 81h, 0BFh, 1Fh
   181                              <1>  	; 09/11/2020
   182                              <1> 	;db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0BFh, 1Fh
   183 00006718 004F                <1> 	db	00h, 4Fh
   184                              <1> vga_p_cm_pos equ $ - vga_mode_03h
   185 0000671A 0D0E00000000        <1> 	db	0Dh, 0Eh, 00h, 00h, 00h, 00h
   186 00006720 9C8E8F281F96B9A3    <1>  	db	9Ch, 8Eh, 8Fh, 28h, 1Fh, 96h, 0B9h, 0A3h
   187 00006728 FF                  <1> 	db	0FFh	; crtc_regs (25)
   188 00006729 0001020304051407    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 14h, 07h
   189 00006731 38393A3B3C3D3E3F    <1>  	db	38h, 39h, 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh
   190                              <1>  	;db	0Ch, 00h, 0Fh, 08h  ; actl regs (20)
   191 00006739 0C000F00            <1> 	db	0Ch, 00h, 0Fh, 00h  ; 19/11/2020
   192 0000673D 0000000000100E0FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 10h, 0Eh, 0Fh, 0FFh ; grdc regs (9)
   193                              <1> 	; 09/11/2020
   194                              <1> 	;db	00h, 00h, 00h, 00h, 00h, 10h, 0Eh, 00h, 0FFh ; grdc regs (9)
   195                              <1> vga_mode_01h:	; mode 01h, 40*25 text, CGA colors
   196 00006746 2818100008          <1> 	db	40, 24, 16, 00h, 08h ; tw, th-1, ch, slength
   197 0000674B 08030002            <1> 	db	08h, 03h, 00h, 02h  ; sequ regs
   198 0000674F 67                  <1> 	db	67h	; misc reg
   199 00006750 2D2728902BA0BF1F    <1> 	db	2Dh, 27h, 28h, 90h, 2Bh, 0A0h, 0BFh, 1Fh
   200 00006758 004F0D0E00000000    <1> 	db	00h, 4Fh, 0Dh, 0Eh, 00h, 00h, 00h, 00h
   201 00006760 9C8E8F141F96B9A3    <1> 	db	9Ch, 8Eh, 8Fh, 14h, 1Fh, 96h, 0B9h, 0A3h
   202 00006768 FF                  <1> 	db	0FFh	; crtc_regs
   203 00006769 0001020304051407    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 14h, 07h
   204 00006771 38393A3B3C3D3E3F    <1> 	db	38h, 39h, 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh
   205                              <1>  	;db	0Ch, 00h, 0Fh, 08h  ; actl regs (20)
   206 00006779 0C000F00            <1> 	db	0Ch, 00h, 0Fh, 00h  ; 19/11/2020
   207 0000677D 0000000000100E0FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 10h, 0Eh, 0Fh, 0FFh ; grdc regs
   208                              <1> ;vga_mode_07h:	; mode 07h, 80*25 text, mono color
   209                              <1> ;	db	80, 24, 16, 00h, 10h  ; tw, th-1, ch, slength
   210                              <1> ;	db	00h, 03h, 00h, 02h ; sequ regs
   211                              <1> ;	db	66h	; misc reg
   212                              <1> ;	db	5Fh, 4Fh, 50h, 82h, 55h, 81h, 0BFh, 1Fh
   213                              <1> ;	db	00h, 4Fh, 0Dh, 0Eh, 00h, 00h, 00h, 00h
   214                              <1> ;	db	9Ch, 8Eh, 8Fh, 28h, 0Fh, 96h, 0B9h, 0A3h
   215                              <1> ;	db	0FFh	; crtc regs
   216                              <1> ;	db	00h, 08h, 08h, 08h, 08h, 08h, 08h, 08h
   217                              <1> ;	db	10h, 18h, 18h, 18h, 18h, 18h, 18h, 18h
   218                              <1> ;	db	0Eh, 00h, 0Fh, 08h  ; actl regs
   219                              <1> ;	db	00h, 00h, 00h, 00h, 00h, 10h, 0Ah, 0Fh, 0FFh ; grdc regs
   220                              <1> vga_mode_04h:	; 320*200 graphics, 4 colors, CGA
   221                              <1> 	; 11/11/2020
   222 00006786 2818080040          <1> 	db	40, 24, 8, 00h, 40h ; tw, th-1, ch, slength
   223 0000678B 09030002            <1> 	db	09h, 03h, 00h, 02h ; sequ regs
   224 0000678F 63                  <1> 	db	63h	; misc reg
   225 00006790 2D2728902B80BF1F    <1> 	db	2Dh, 27h, 28h, 90h, 2Bh, 80h, 0BFh, 1Fh
   226 00006798 00C1000000000000    <1> 	db	00h, 0C1h, 00h, 00h, 00h, 00h, 00h, 00h
   227 000067A0 9C8E8F140096B9A2    <1> 	db	9Ch, 8Eh, 8Fh, 14h, 00h, 96h, 0B9h, 0A2h
   228 000067A8 FF                  <1> 	db	0FFh	; crtc_regs
   229 000067A9 0013151702040607    <1> 	db	00h, 13h, 15h, 17h, 02h, 04h, 06h, 07h
   230 000067B1 1011121314151617    <1> 	db	10h, 11h, 12h, 13h, 14h, 15h, 16h, 17h
   231 000067B9 01000300            <1> 	db	01h, 00h, 03h, 00h ; actl regs
   232 000067BD 0000000000300F0FFF  <1> 	db 	00h, 00h, 00h, 00h, 00h, 30h, 0Fh, 0Fh, 0FFh ; grdc regs
   233                              <1> vga_mode_06h:	; 640*200 graphics, 2 colors, CGA
   234                              <1> 	; 11/11/2020
   235 000067C6 5018080040          <1> 	db	80, 24, 8, 00h, 40h   ;	tw, th-1, ch, slength
   236 000067CB 01010006            <1> 	db	01h, 01h, 00h, 06h ; sequ regs
   237 000067CF 63                  <1> 	db	63h	; misc reg
   238 000067D0 5F4F50825480BF1F    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0BFh, 1Fh
   239 000067D8 00C1000000000000    <1> 	db	00h, 0C1h, 00h, 00h, 00h, 00h, 00h, 00h
   240 000067E0 9C8E8F280096B9C2    <1> 	db	9Ch, 8Eh, 8Fh, 28h, 00h, 96h, 0B9h, 0C2h
   241 000067E8 FF                  <1> 	db	0FFh	; crtc regs
   242 000067E9 0017171717171717    <1> 	db	00h, 17h, 17h, 17h, 17h, 17h, 17h, 17h
   243 000067F1 1717171717171717    <1> 	db	17h, 17h, 17h, 17h, 17h, 17h, 17h, 17h
   244 000067F9 01000100            <1> 	db	01h, 00h, 01, 00h  ; actl regs
   245 000067FD 0000000000000D0FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 0Dh, 0Fh, 0FFh ; grdc regs
   246                              <1> vga_mode_13h:  ; mode 13h, 300*200, 256 colors, linear
   247                              <1> 	; 11/11/2020
   248                              <1> 	;db 	40, 24, 8, 00h, 20h ; tw, th-1, ch, slength (5)
   249                              <1> 	; 23/11/2020 - 10/11/2020
   250 00006806 28180800FA          <1> 	db 	40, 24, 8, 00h, 0FAh ; tw, th-1, ch, slength (5)
   251 0000680B 010F000E            <1> 	db	01h, 0Fh, 00h, 0Eh ; sequ regs (4)
   252 0000680F 63                  <1> 	db	63h	; misc reg (1)
   253 00006810 5F4F50825480BF1F    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0BFh, 1Fh 
   254 00006818 0041000000000000    <1> 	db 	00h, 041h, 00h, 00h, 00h, 00h, 00h, 00h
   255 00006820 9C8E8F284096B9A3    <1> 	db	9Ch, 8Eh, 8Fh, 28h, 40h, 96h, 0B9h, 0A3h
   256 00006828 FF                  <1> 	db	0FFh	; crtc regs (25)
   257 00006829 0001020304050607    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 06h, 07h
   258 00006831 08090A0B0C0D0E0F    <1>  	db	08h, 09h, 0Ah, 0Bh, 0Ch, 0Dh, 0Eh, 0Fh
   259 00006839 41000F00            <1>  	db	41h, 00h, 0Fh, 00h  ; actl regs (20)
   260                              <1> 	; 10/11/2020
   261                              <1>  	;db	41h, 01h, 0Fh, 13h  ; actl regs (20) 
   262 0000683D 000000000040050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 40h, 05h, 0Fh, 0FFh ; grdc regs (9)
   263                              <1> vga_mode_setl equ $ - vga_mode_13h  ; = 64
   264                              <1> vga_mode_F0h:  ; mode X ; 320*240, 256 colors, planar
   265 00006846 2818080000          <1> 	db 	40, 24, 8, 00h, 00h ; tw, th-1, ch, slength
   266 0000684B 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   267 0000684F E3                  <1> 	db	0E3h	; misc reg
   268 00006850 5F4F508254800D3E    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0Dh, 3Eh 
   269 00006858 0041000000000000    <1>  	db 	00h, 41h, 00h, 00h, 00h, 00h, 00h, 00h
   270 00006860 EAACDF2800E706E3    <1> 	db	0EAh, 0ACh, 0DFh, 28h, 00h, 0E7h, 06h, 0E3h
   271 00006868 FF                  <1> 	db	0FFh	; crtc regs (25)
   272 00006869 0001020304050607    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 06h, 07h
   273 00006871 08090A0B0C0D0E0F    <1>  	db	08h, 09h, 0Ah, 0Bh, 0Ch, 0Dh, 0Eh, 0Fh
   274 00006879 41000F00            <1>  	db	41h, 00h, 0Fh, 00h  ; actl regs
   275 0000687D 000000000040050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 40h, 05h, 0Fh, 0FFh ; grdc regs
   276                              <1> vga_mode_12h:  ; mode 12h, 640*480, 16 colors, planar
   277                              <1> 	; 11/11/2020
   278                              <1>  	;db 	80, 29, 16, 0, 0 ; tw, th-1, ch, slength
   279                              <1> 	; 09/11/2020
   280 00006886 501D1000A0          <1>  	db 	80, 29, 16, 00h, 0A0h ; tw, th-1, ch, slength
   281 0000688B 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   282 0000688F E3                  <1> 	db 	0E3h	; misc reg
   283 00006890 5F4F508254800B3E    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0Bh, 3Eh
   284                              <1> 	; 09/11/2020
   285                              <1> 	;db	5Fh, 4Fh, 50h, 82h, 53h, 9Fh, 0Bh, 3Eh
   286 00006898 0040000000000000    <1> 	db	00h, 40h, 00h, 00h, 00h, 00h, 00h, 00h
   287 000068A0 EA8CDF2800E704E3    <1>  	db	0EAh, 8Ch, 0DFh, 28h, 00h, 0E7h, 04h, 0E3h
   288                              <1> 	; 09/11/2020
   289                              <1>  	;db	0E9h, 8Bh, 0DFh, 28h, 00h, 0E7h, 04h, 0E3h
   290 000068A8 FF                  <1> 	db	0FFh	; crtc regs
   291 000068A9 0001020304051407    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 14h, 07h
   292 000068B1 38393A3B3C3D3E3F    <1> 	db	38h, 39h, 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh
   293 000068B9 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   294 000068BD 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   295                              <1> vga_mode_6Ah:  ; mode 6Ah, 800*600, 16 colors, planar
   296                              <1> 	; 11/11/2020
   297 000068C6 6424100000          <1>  	db 	100, 36, 16, 00h, 00h ; tw, th-1, ch, slength
   298 000068CB 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   299 000068CF E3                  <1> 	db 	0E3h	; misc reg
   300 000068D0 7F6363836B1B72F0    <1> 	db	7Fh, 63h, 63h, 83h, 6Bh, 1Bh, 72h, 0F0h
   301 000068D8 0060000000000000    <1> 	db	00h, 60h, 00h, 00h, 00h, 00h, 00h, 00h
   302 000068E0 598D5732005773E3    <1>  	db	59h, 8Dh, 57h, 32h, 00h, 57h, 73h, 0E3h
   303 000068E8 FF                  <1> 	db	0FFh	; crtc regs
   304 000068E9 0001020304051407    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 14h, 07h
   305 000068F1 38393A3B3C3D3E3F    <1> 	db	38h, 39h, 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh
   306 000068F9 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   307 000068FD 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   308                              <1> vga_mode_0Dh:  ; mode 0Dh, 320*200, 16 colors, planar
   309 00006906 2818080020          <1>  	db 	40, 24, 8, 00h, 20h ; tw, th-1, ch, slength
   310 0000690B 090F0006            <1> 	db	09h, 0Fh, 00h, 06h ; sequ regs
   311 0000690F 63                  <1> 	db 	63h	; misc reg
   312 00006910 2D2728902B80BF1F    <1> 	db	2Dh, 27h, 28h, 90h, 2Bh, 80h, 0BFh, 1Fh
   313 00006918 00C0000000000000    <1> 	db	00h, 0C0h, 00h, 00h, 00h, 00h, 00h, 00h
   314 00006920 9C8E8F140096B9E3    <1>  	db	9Ch, 8Eh, 8Fh, 14h, 00h, 96h, 0B9h, 0E3h
   315 00006928 FF                  <1> 	db	0FFh	; crtc regs
   316 00006929 0001020304050607    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 06h, 07h
   317 00006931 1011121314151617    <1> 	db	10h, 11h, 12h, 13h, 14h, 15h, 16h, 17h
   318 00006939 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   319 0000693D 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   320                              <1> vga_mode_0Eh:  ; mode 0Eh, 640*200, 16 colors, planar
   321 00006946 5018080040          <1>  	db 	80, 24, 8, 00h, 40h ; tw, th-1, ch, slength
   322 0000694B 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   323 0000694F 63                  <1> 	db 	63h	; misc reg
   324 00006950 5F4F50825480BF1F    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0BFh, 1Fh
   325 00006958 00C0000000000000    <1> 	db	00h, 0C0h, 00h, 00h, 00h, 00h, 00h, 00h
   326 00006960 9C8E8F280096B9E3    <1>  	db	9Ch, 8Eh, 8Fh, 28h, 00h, 96h, 0B9h, 0E3h
   327 00006968 FF                  <1> 	db	0FFh	; crtc regs
   328 00006969 0001020304050607    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 06h, 07h
   329 00006971 1011121314151617    <1> 	db	10h, 11h, 12h, 13h, 14h, 15h, 16h, 17h
   330 00006979 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   331 0000697D 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   332                              <1> vga_mode_10h: ; mode 10h, 640*350, 16 colors, planar
   333 00006986 50180E0080          <1>  	db 	80, 24, 14, 00h, 80h ; tw, th-1, ch, slength
   334 0000698B 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   335 0000698F A3                  <1> 	db 	0A3h	; misc reg
   336 00006990 5F4F50825480BF1F    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0BFh, 1Fh
   337 00006998 0040000000000000    <1> 	db	00h, 40h, 00h, 00h, 00h, 00h, 00h, 00h
   338 000069A0 83855D280F63BAE3    <1>  	db	83h, 85h, 5Dh, 28h, 0Fh, 63h, 0BAh, 0E3h
   339 000069A8 FF                  <1> 	db	0FFh	; crtc regs
   340 000069A9 0001020304051407    <1> 	db	00h, 01h, 02h, 03h, 04h, 05h, 14h, 07h
   341 000069B1 38393A3B3C3D3E3F    <1> 	db	38h, 39h, 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh
   342 000069B9 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   343 000069BD 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   344                              <1> vga_mode_11h: ; mode 11h, 640*480, mono color, planar
   345                              <1>  	; 11/11/2020
   346 000069C6 501D1000A0          <1> 	db 	80, 29, 16, 00h, 0A0h ; tw, th-1, ch, slength
   347 000069CB 010F0006            <1> 	db	01h, 0Fh, 00h, 06h ; sequ regs
   348 000069CF E3                  <1> 	db 	0E3h	; misc reg
   349 000069D0 5F4F508254800B3E    <1> 	db	5Fh, 4Fh, 50h, 82h, 54h, 80h, 0Bh, 3Eh
   350 000069D8 0040000000000000    <1> 	db	00h, 40h, 00h, 00h, 00h, 00h, 00h, 00h
   351 000069E0 EA8CDF2800E704C3    <1>  	db	0EAh, 8Ch, 0DFh, 28h, 00h, 0E7h, 04h, 0C3h ; 11/11/2020
   352 000069E8 FF                  <1> 	db	0FFh	; crtc regs
   353 000069E9 003F003F003F003F    <1> 	db	00h, 3Fh, 00h, 3Fh, 00h, 3Fh, 00h, 3Fh
   354 000069F1 003F003F003F003F    <1> 	db	00h, 3Fh, 00h, 3Fh, 00h, 3Fh, 00h, 3Fh
   355 000069F9 01000F00            <1> 	db	01h, 00h, 0Fh, 00h  ; actl regs
   356 000069FD 000000000000050FFF  <1> 	db	00h, 00h, 00h, 00h, 00h, 00h, 05h, 0Fh, 0FFh ; grdc regs
   357                              <1> end_of_vga_params:
   358                              <1> 
   359                              <1> ; /// End Of VIDEO DATA ///
   360                              <1> 
   361                              <1> ; 23/11/2020
   362                              <1> ; VBE 2 BOCHS/QEMU emulator extensions 
   363                              <1> ;	for TRDOS 386 v2 kernel (video bios)  
   364                              <1> 
   365                              <1> ; vbetables.h by Volker Rupper (02/01/2020)
   366                              <1> 
   367                              <1> b_vbe_modes:
   368                              <1> 	;/* standard VESA modes */	
   369 00006A06 0001800290010800    <1> 	dw 100h,  640, 400,  8
   370 00006A0E 01018002E0010800    <1> 	dw 101h,  640, 480,  8
   371 00006A16 0301200358020800    <1> 	dw 103h,  800, 600,  8
   372 00006A1E 0501000400030800    <1> 	dw 105h, 1024, 768,  8
   373 00006A26 0E014001C8001000    <1> 	dw 10Eh,  320, 200, 16
   374 00006A2E 0F014001C8001800    <1> 	dw 10Fh,  320, 200, 24
   375 00006A36 11018002E0011000    <1> 	dw 111h,  640, 480, 16
   376 00006A3E 12018002E0011800    <1> 	dw 112h,  640, 480, 24
   377 00006A46 1401200358021000    <1> 	dw 114h,  800, 600, 16
   378 00006A4E 1501200358021800    <1> 	dw 115h,  800, 600, 24
   379 00006A56 1701000400031000    <1> 	dw 117h, 1024, 768, 16
   380 00006A5E 1801000400031800    <1> 	dw 118h, 1024, 768, 24
   381                              <1> 
   382                              <1> ;/* BOCHS/PLEX86 'own' mode numbers */
   383 00006A66 40014001C8002000    <1> 	dw 140h,  320,  200, 32
   384 00006A6E 4101800290012000    <1> 	dw 141h,  640,  400, 32
   385 00006A76 42018002E0012000    <1> 	dw 142h,  640,  480, 32
   386 00006A7E 4301200358022000    <1> 	dw 143h,  800,  600, 32
   387 00006A86 4401000400032000    <1> 	dw 144h, 1024,  768, 32
   388 00006A8E 46014001C8000800    <1> 	dw 146h,  320,  200,  8
   389 00006A96 8D010005D0021000    <1> 	dw 18Dh, 1280,  720, 16
   390 00006A9E 8E010005D0021800    <1> 	dw 18Eh, 1280,  720, 24
   391 00006AA6 8F010005D0022000    <1> 	dw 18Fh, 1280,  720, 32
   392 00006AAE 9001800738041000    <1> 	dw 190h, 1920, 1080, 16
   393 00006AB6 9101800738041800    <1> 	dw 191h, 1920, 1080, 24
   394 00006ABE 9201800738042000    <1> 	dw 192h, 1920, 1080, 32
   395                              <1> 
   396                              <1> end_of_b_vbe_modes:
   397                              <1> 
   398                              <1> MA1 equ VBE_MODE_ATTRIBUTE_SUPPORTED
   399                              <1> MA2 equ VBE_MODE_ATTRIBUTE_EXTENDED_INFO_AVAILABLE
   400                              <1> MA3 equ VBE_MODE_ATTRIBUTE_COLOR_MODE
   401                              <1> MA4 equ VBE_MODE_ATTRIBUTE_LINEAR_FRAME_BUFFER_MODE
   402                              <1> MA5 equ	VBE_MODE_ATTRIBUTE_GRAPHICS_MODE
   403                              <1> 
   404                              <1> MODE_ATTRIBUTES equ MA1|MA2|MA3|MA4|MA5
   405                              <1> 
   406                              <1> WA1 equ VBE_WINDOW_ATTRIBUTE_RELOCATABLE
   407                              <1> WA2 equ	VBE_WINDOW_ATTRIBUTE_READABLE
   408                              <1> WA3 equ VBE_WINDOW_ATTRIBUTE_WRITEABLE
   409                              <1> 
   410                              <1> WINA_ATTRIBUTES equ WA1|WA2|WA3
   411                              <1> 
   412                              <1> ; 24/11/2020
   413                              <1> 
   414                              <1> %if 0
   415                              <1> 
   416                              <1> MODE_INFO_LIST: 
   417                              <1> 
   418                              <1> ; 24/11/2020
   419                              <1> ; '%if 0' disables 24 mode info tables here, until %endif 
   420                              <1> ; ('set_mode_info_list' will set only 1 list for selected mode)
   421                              <1> ; (Purpose: To save about 1 KB kernel size by removing fixed data)
   422                              <1> 
   423                              <1> 			dw	0100h ; 640x400x8 
   424                              <1> ModeAttributes1: 	dw	MODE_ATTRIBUTES
   425                              <1> WinAAttributes1: 	db	WINA_ATTRIBUTES
   426                              <1> WinBAttributes1: 	db	0
   427                              <1> WinGranularity1: 	dw	VBE_DISPI_BANK_SIZE_KB
   428                              <1> WinSize1: 		dw	VBE_DISPI_BANK_SIZE_KB
   429                              <1> WinASegment1:		dw	VGAMEM_GRAPH
   430                              <1> WinBSegment1:		dw	0000h
   431                              <1> WinFuncPtr1:		dd	0
   432                              <1> BytesPerScanLine1: 	dw	640
   433                              <1> XResolution1:		dw	640
   434                              <1> YResolution1:		dw	400
   435                              <1> XCharSize1:		db	8
   436                              <1> YCharSize1:		db	16
   437                              <1> NumberOfPlanes1: 	db	1
   438                              <1> BitsPerPixel1:		db	8
   439                              <1> NumberOfBanks1:		db	4
   440                              <1> MemoryModel1:		db	VBE_MEMORYMODEL_PACKED_PIXEL
   441                              <1> BankSize1:		db	0
   442                              <1> NumberOfImagePages1: 	db	64
   443                              <1> Reserved_page1:		db	0
   444                              <1> RedMaskSize1:		db	0
   445                              <1> RedFieldPosition1: 	db	0
   446                              <1> GreenMaskSize1:		db	0
   447                              <1> GreenFieldPosition1: 	db	0
   448                              <1> BlueMaskSize1:		db	0
   449                              <1> BlueFieldPosition1: 	db	0
   450                              <1> RsvdMaskSize1: 		db	0
   451                              <1> RsvdFieldPosition1: 	db	0
   452                              <1> DirectColorModeInfo1: 	db	0
   453                              <1> PhysBasePtr1:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   454                              <1> OffScreenMemOffset1: 	dd	0
   455                              <1> OffScreenMemSize1: 	dw	0
   456                              <1> LinBytesPerScanLine1: 	dw	640
   457                              <1> BnkNumberOfPages1: 	db	0
   458                              <1> LinNumberOfPages1: 	db	0
   459                              <1> LinRedMaskSize1:	db	0
   460                              <1> LinRedFieldPosition1: 	db	0
   461                              <1> LinGreenMaskSize1: 	db	0
   462                              <1> LinGreenFieldPosition1: db	0
   463                              <1> LinBlueMaskSize1: 	db	0
   464                              <1> LinBlueFieldPosition1: 	db	0
   465                              <1> LinRsvdMaskSize1: 	db	0
   466                              <1> LinRsvdFieldPosition1: 	db	0
   467                              <1> MaxPixelClock1:		dd	0
   468                              <1> 
   469                              <1> 			dw	0101h ; 640x480x8
   470                              <1> ModeAttributes2: 	dw	MODE_ATTRIBUTES
   471                              <1> WinAAttributes2: 	db	WINA_ATTRIBUTES
   472                              <1> WinBAttributes2: 	db	0
   473                              <1> WinGranularity2: 	dw	VBE_DISPI_BANK_SIZE_KB
   474                              <1> WinSize2: 		dw	VBE_DISPI_BANK_SIZE_KB
   475                              <1> WinASegment2:		dw	VGAMEM_GRAPH
   476                              <1> WinBSegment2:		dw	0000h
   477                              <1> WinFuncPtr2:		dd	0
   478                              <1> BytesPerScanLine2:	dw	640
   479                              <1> XResolution2:		dw	640
   480                              <1> YResolution2:		dw	480
   481                              <1> XCharSize2:		db	8
   482                              <1> YCharSize2:		db	16
   483                              <1> NumberOfPlanes2:	db	1
   484                              <1> BitsPerPixel2:		db	8
   485                              <1> NumberOfBanks2:		db	5
   486                              <1> MemoryModel2:		db	VBE_MEMORYMODEL_PACKED_PIXEL
   487                              <1> BankSize2:		db	0
   488                              <1> NumberOfImagePages2:	db	53
   489                              <1> Reserved_page2:		db	0
   490                              <1> RedMaskSize2:		db	0
   491                              <1> RedFieldPosition2:	db	0
   492                              <1> GreenMaskSize2:		db	0
   493                              <1> GreenFieldPosition2:	db	0
   494                              <1> BlueMaskSize2:		db	0
   495                              <1> BlueFieldPosition2:	db	0
   496                              <1> RsvdMaskSize2:		db	0
   497                              <1> RsvdFieldPosition2:	db	0
   498                              <1> DirectColorModeInfo2:	db	0
   499                              <1> PhysBasePtr2:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   500                              <1> OffScreenMemOffset2:	dd	0
   501                              <1> OffScreenMemSize2:	dw	0
   502                              <1> LinBytesPerScanLine2:	dw	640
   503                              <1> BnkNumberOfPages2: 	db	0
   504                              <1> LinNumberOfPages2: 	db	0
   505                              <1> LinRedMaskSize2:	db	0
   506                              <1> LinRedFieldPosition2: 	db	0
   507                              <1> LinGreenMaskSize2: 	db	0
   508                              <1> LinGreenFieldPosition2: db	0
   509                              <1> LinBlueMaskSize2: 	db	0
   510                              <1> LinBlueFieldPosition2: 	db	0
   511                              <1> LinRsvdMaskSize2: 	db	0
   512                              <1> LinRsvdFieldPosition2: 	db	0
   513                              <1> MaxPixelClock2:		dd	0
   514                              <1> 			
   515                              <1> 			dw	0103h ; 800x600x8
   516                              <1> ModeAttributes3: 	dw	MODE_ATTRIBUTES
   517                              <1> WinAAttributes3: 	db	WINA_ATTRIBUTES
   518                              <1> WinBAttributes3: 	db	0
   519                              <1> WinGranularity3: 	dw	VBE_DISPI_BANK_SIZE_KB
   520                              <1> WinSize3: 		dw	VBE_DISPI_BANK_SIZE_KB
   521                              <1> WinASegment3:		dw	VGAMEM_GRAPH
   522                              <1> WinBSegment3:		dw	0000h
   523                              <1> WinFuncPtr3:		dd	0
   524                              <1> BytesPerScanLine3:	dw	800
   525                              <1> XResolution3:		dw	800
   526                              <1> YResolution3:		dw	600
   527                              <1> XCharSize3:		db	8
   528                              <1> YCharSize3:		db	16
   529                              <1> NumberOfPlanes3:	db	1
   530                              <1> BitsPerPixel3:		db	8
   531                              <1> NumberOfBanks3:		db	8
   532                              <1> MemoryModel3:		db	VBE_MEMORYMODEL_PACKED_PIXEL
   533                              <1> BankSize3:		db	0
   534                              <1> NumberOfImagePages3:	db	33
   535                              <1> Reserved_page3:		db	0
   536                              <1> RedMaskSize3:		db	0
   537                              <1> RedFieldPosition3:	db	0
   538                              <1> GreenMaskSize3:		db	0
   539                              <1> GreenFieldPosition3:	db	0
   540                              <1> BlueMaskSize3:		db	0
   541                              <1> BlueFieldPosition3:	db	0
   542                              <1> RsvdMaskSize3:		db	0
   543                              <1> RsvdFieldPosition3:	db	0
   544                              <1> DirectColorModeInfo3:	db	0
   545                              <1> PhysBasePtr3:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   546                              <1> OffScreenMemOffset3:	dd	0
   547                              <1> OffScreenMemSize3:	dw	0
   548                              <1> LinBytesPerScanLine3:	dw	800
   549                              <1> BnkNumberOfPages3: 	db	0
   550                              <1> LinNumberOfPages3: 	db	0
   551                              <1> LinRedMaskSize3:	db	0
   552                              <1> LinRedFieldPosition3: 	db	0
   553                              <1> LinGreenMaskSize3: 	db	0
   554                              <1> LinGreenFieldPosition: 	db	0
   555                              <1> LinBlueMaskSize: 	db	0
   556                              <1> LinBlueFieldPosition: 	db	0
   557                              <1> LinRsvdMaskSize: 	db	0
   558                              <1> LinRsvdFieldPosition: 	db	0
   559                              <1> MaxPixelClock:		dd	0
   560                              <1> 			
   561                              <1> 			dw	0105h ; 1024x768x8
   562                              <1> ModeAttributes4: 	dw	MODE_ATTRIBUTES
   563                              <1> WinAAttributes4: 	db	WINA_ATTRIBUTES
   564                              <1> WinBAttributes4: 	db	0
   565                              <1> WinGranularity4: 	dw	VBE_DISPI_BANK_SIZE_KB
   566                              <1> WinSize4: 		dw	VBE_DISPI_BANK_SIZE_KB
   567                              <1> WinASegment4:		dw	VGAMEM_GRAPH
   568                              <1> WinBSegment4:		dw	0000h
   569                              <1> WinFuncPtr4:		dd	0
   570                              <1> BytesPerScanLine4:	dw	1024
   571                              <1> XResolution4:		dw	1024
   572                              <1> YResolution4:		dw	768
   573                              <1> XCharSize4:		db	8
   574                              <1> YCharSize4:		db	16
   575                              <1> NumberOfPlanes4:	db	1
   576                              <1> BitsPerPixel4:		db	8
   577                              <1> NumberOfBanks4:		db	12
   578                              <1> MemoryModel4:		db	VBE_MEMORYMODEL_PACKED_PIXEL
   579                              <1> BankSize4:		db	0
   580                              <1> NumberOfImagePages4:	db	20
   581                              <1> Reserved_page4:		db	0
   582                              <1> RedMaskSize4:		db	0
   583                              <1> RedFieldPosition4:	db	0
   584                              <1> GreenMaskSize4:		db	0
   585                              <1> GreenFieldPosition4:	db	0
   586                              <1> BlueMaskSize4:		db	0
   587                              <1> BlueFieldPosition4:	db	0
   588                              <1> RsvdMaskSize4:		db	0
   589                              <1> RsvdFieldPosition4:	db	0
   590                              <1> DirectColorModeInfo4:	db	0
   591                              <1> PhysBasePtr4:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   592                              <1> OffScreenMemOffset4:	dd	0
   593                              <1> OffScreenMemSize4:	dw	0
   594                              <1> LinBytesPerScanLine4:	dw	1024
   595                              <1> BnkNumberOfPages4: 	db	0
   596                              <1> LinNumberOfPages4: 	db	0
   597                              <1> LinRedMaskSize4:	db	0
   598                              <1> LinRedFieldPosition4: 	db	0
   599                              <1> LinGreenMaskSize4: 	db	0
   600                              <1> LinGreenFieldPosition4: db	0
   601                              <1> LinBlueMaskSize4: 	db	0
   602                              <1> LinBlueFieldPosition4: 	db	0
   603                              <1> LinRsvdMaskSize4: 	db	0
   604                              <1> LinRsvdFieldPosition4: 	db	0
   605                              <1> MaxPixelClock4:		dd	0
   606                              <1> 
   607                              <1> 			dw	010Eh ; 320x200x16
   608                              <1> ModeAttributes5: 	dw	MODE_ATTRIBUTES
   609                              <1> WinAAttributes5: 	db	WINA_ATTRIBUTES
   610                              <1> WinBAttributes5: 	db	0
   611                              <1> WinGranularity5: 	dw	VBE_DISPI_BANK_SIZE_KB
   612                              <1> WinSize5: 		dw	VBE_DISPI_BANK_SIZE_KB
   613                              <1> WinASegment5:		dw	VGAMEM_GRAPH
   614                              <1> WinBSegment5:		dw	0000h
   615                              <1> WinFuncPtr5:		dd	0
   616                              <1> BytesPerScanLine5:	dw	640
   617                              <1> XResolution5:		dw	320
   618                              <1> YResolution5:		dw	200
   619                              <1> XCharSize5:		db	8
   620                              <1> YCharSize5:		db	16
   621                              <1> NumberOfPlanes5:	db	1
   622                              <1> BitsPerPixel5:		db	16
   623                              <1> NumberOfBanks5:		db	2
   624                              <1> MemoryModel5:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   625                              <1> BankSize5:		db	0
   626                              <1> NumberOfImagePages5:	db	130
   627                              <1> Reserved_page5:		db	0
   628                              <1> RedMaskSize5:		db	5
   629                              <1> RedFieldPosition5:	db	11
   630                              <1> GreenMaskSize5:		db	6
   631                              <1> GreenFieldPosition5:	db	5
   632                              <1> BlueMaskSize5:		db	5
   633                              <1> BlueFieldPosition5:	db	0
   634                              <1> RsvdMaskSize5:		db	0
   635                              <1> RsvdFieldPosition5:	db	0
   636                              <1> DirectColorModeInfo5:	db	0
   637                              <1> PhysBasePtr5:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   638                              <1> OffScreenMemOffset5:	dd	0
   639                              <1> OffScreenMemSize5:	dw	0
   640                              <1> LinBytesPerScanLine5:	dw	640
   641                              <1> BnkNumberOfPages5: 	db	0
   642                              <1> LinNumberOfPages5: 	db	0
   643                              <1> LinRedMaskSize5:	db	5
   644                              <1> LinRedFieldPosition5:	db	11
   645                              <1> LinGreenMaskSize5:	db	6
   646                              <1> LinGreenFieldPosition5:	db	5
   647                              <1> LinBlueMaskSize5:	db	5
   648                              <1> LinBlueFieldPosition5:	db	0
   649                              <1> LinRsvdMaskSize5:	db	0
   650                              <1> LinRsvdFieldPosition5:	db	0
   651                              <1> MaxPixelClock5:		dd	0
   652                              <1> 	
   653                              <1> 			dw	010Fh ; 320x200x24
   654                              <1> ModeAttributes6: 	dw	MODE_ATTRIBUTES
   655                              <1> WinAAttributes6: 	db	WINA_ATTRIBUTES
   656                              <1> WinBAttributes6: 	db	0
   657                              <1> WinGranularity6: 	dw	VBE_DISPI_BANK_SIZE_KB
   658                              <1> WinSize6: 		dw	VBE_DISPI_BANK_SIZE_KB
   659                              <1> WinASegment6:		dw	VGAMEM_GRAPH
   660                              <1> WinBSegment6:		dw	0000h
   661                              <1> WinFuncPtr6:		dd	0
   662                              <1> BytesPerScanLine6:	dw	960
   663                              <1> XResolution6:		dw	320
   664                              <1> YResolution6:		dw	200
   665                              <1> XCharSize6:		db	8
   666                              <1> YCharSize6:		db	16
   667                              <1> NumberOfPlanes6:	db	1
   668                              <1> BitsPerPixel6:		db	24
   669                              <1> NumberOfBanks6:		db	3
   670                              <1> MemoryModel6:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   671                              <1> BankSize6:		db	0
   672                              <1> NumberOfImagePages6:	db	86
   673                              <1> Reserved_page6:		db	0
   674                              <1> RedMaskSize6:		db	8
   675                              <1> RedFieldPosition6:	db	16
   676                              <1> GreenMaskSize6:		db	8
   677                              <1> GreenFieldPosition6:	db	8
   678                              <1> BlueMaskSize6:		db	8
   679                              <1> BlueFieldPosition6:	db	0
   680                              <1> RsvdMaskSize6:		db	0
   681                              <1> RsvdFieldPosition6:	db	0
   682                              <1> DirectColorModeInfo6:	db	0
   683                              <1> PhysBasePtr6:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   684                              <1> OffScreenMemOffset6:	dd	0
   685                              <1> OffScreenMemSize6:	dw	0
   686                              <1> LinBytesPerScanLine6:	dw	960
   687                              <1> BnkNumberOfPages6: 	db	0
   688                              <1> LinNumberOfPages6: 	db	0
   689                              <1> LinRedMaskSize6:	db	8
   690                              <1> LinRedFieldPosition6:	db	16
   691                              <1> LinGreenMaskSize6:	db	8
   692                              <1> LinGreenFieldPosition6:	db	8
   693                              <1> LinBlueMaskSize6:	db	8
   694                              <1> LinBlueFieldPosition6:	db	0
   695                              <1> LinRsvdMaskSize6:	db	0
   696                              <1> LinRsvdFieldPosition6:	db	0
   697                              <1> MaxPixelClock6:		dd	0
   698                              <1> 	
   699                              <1> 			dw	0111h ; 640x480x16
   700                              <1> ModeAttributes7: 	dw	MODE_ATTRIBUTES
   701                              <1> WinAAttributes7: 	db	WINA_ATTRIBUTES
   702                              <1> WinBAttributes7: 	db	0
   703                              <1> WinGranularity7: 	dw	VBE_DISPI_BANK_SIZE_KB
   704                              <1> WinSize7: 		dw	VBE_DISPI_BANK_SIZE_KB
   705                              <1> WinASegment7:		dw	VGAMEM_GRAPH
   706                              <1> WinBSegment7:		dw	0000h
   707                              <1> WinFuncPtr7:		dd	0
   708                              <1> BytesPerScanLine7:	dw	1280
   709                              <1> XResolution7:		dw	640
   710                              <1> YResolution7:		dw	480
   711                              <1> XCharSize7:		db	8
   712                              <1> YCharSize7:		db	16
   713                              <1> NumberOfPlanes7:	db	1
   714                              <1> BitsPerPixel7:		db	16
   715                              <1> NumberOfBanks7:		db	10
   716                              <1> MemoryModel7:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   717                              <1> BankSize7:		db	0
   718                              <1> NumberOfImagePages7:	db	26
   719                              <1> Reserved_page7:		db	0
   720                              <1> RedMaskSize7:		db	5
   721                              <1> RedFieldPosition7:	db	11
   722                              <1> GreenMaskSize7:		db	6
   723                              <1> GreenFieldPosition7:	db	5
   724                              <1> BlueMaskSize7:		db	5
   725                              <1> BlueFieldPosition7:	db	0
   726                              <1> RsvdMaskSize7:		db	0
   727                              <1> RsvdFieldPosition7:	db	0
   728                              <1> DirectColorModeInfo7:	db	0
   729                              <1> PhysBasePtr7:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS,
   730                              <1> OffScreenMemOffset7:	dd	0
   731                              <1> OffScreenMemSize7:	dw	0
   732                              <1> LinBytesPerScanLine7:	dw	1280
   733                              <1> BnkNumberOfPages7: 	db	0
   734                              <1> LinNumberOfPages7: 	db	0
   735                              <1> LinRedMaskSize7:	db	5
   736                              <1> LinRedFieldPosition7:	db	11
   737                              <1> LinGreenMaskSize7:	db	6
   738                              <1> LinGreenFieldPosition7:	db	5
   739                              <1> LinBlueMaskSize7:	db	5
   740                              <1> LinBlueFieldPosition7:	db	0
   741                              <1> LinRsvdMaskSize7:	db	0
   742                              <1> LinRsvdFieldPosition7:	db	0
   743                              <1> MaxPixelClock7:		dd	0
   744                              <1> 
   745                              <1> 			dw	0112h ; 640x480x24
   746                              <1> ModeAttributes8: 	dw	MODE_ATTRIBUTES
   747                              <1> WinAAttributes8: 	db	WINA_ATTRIBUTES
   748                              <1> WinBAttributes8: 	db	0
   749                              <1> WinGranularity8: 	dw	VBE_DISPI_BANK_SIZE_KB
   750                              <1> WinSize8: 		dw	VBE_DISPI_BANK_SIZE_KB
   751                              <1> WinASegment8:		dw	VGAMEM_GRAPH
   752                              <1> WinBSegment8:		dw	0000h
   753                              <1> WinFuncPtr8:		dd	0
   754                              <1> BytesPerScanLine8:	dw	1920
   755                              <1> XResolution8:		dw	640
   756                              <1> YResolution8:		dw	480
   757                              <1> XCharSize8:		db	8
   758                              <1> YCharSize8:		db	16
   759                              <1> NumberOfPlanes8:	db	1
   760                              <1> BitsPerPixel8:		db	24
   761                              <1> NumberOfBanks8:		db	15
   762                              <1> MemoryModel8:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   763                              <1> BankSize8:		db	0
   764                              <1> NumberOfImagePages8:	db	17
   765                              <1> Reserved_page8:		db	0
   766                              <1> RedMaskSize8:		db	8
   767                              <1> RedFieldPosition8:	db	16
   768                              <1> GreenMaskSize8:		db	8
   769                              <1> GreenFieldPosition8:	db	8
   770                              <1> BlueMaskSize8:		db	8
   771                              <1> BlueFieldPosition8:	db	0
   772                              <1> RsvdMaskSize8:		db	0
   773                              <1> RsvdFieldPosition8:	db	0
   774                              <1> DirectColorModeInfo8:	db	0
   775                              <1> PhysBasePtr8:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   776                              <1> OffScreenMemOffset8:	dd	0
   777                              <1> OffScreenMemSize8:	dw	0
   778                              <1> LinBytesPerScanLine8:	dw	1920
   779                              <1> BnkNumberOfPages8: 	db	0
   780                              <1> LinNumberOfPages8: 	db	0
   781                              <1> LinRedMaskSize8:	db	8
   782                              <1> LinRedFieldPosition8:	db	16
   783                              <1> LinGreenMaskSize8:	db	8
   784                              <1> LinGreenFieldPosition8:	db	8
   785                              <1> LinBlueMaskSize8:	db	8
   786                              <1> LinBlueFieldPosition8:	db	0
   787                              <1> LinRsvdMaskSize8:	db	0
   788                              <1> LinRsvdFieldPosition8:	db	0
   789                              <1> MaxPixelClock8:		dd	0
   790                              <1> 
   791                              <1> 			dw	0114h ; 800x600x16
   792                              <1> ModeAttributes9: 	dw	MODE_ATTRIBUTES
   793                              <1> WinAAttributes9: 	db	WINA_ATTRIBUTES
   794                              <1> WinBAttributes9: 	db	0
   795                              <1> WinGranularity9: 	dw	VBE_DISPI_BANK_SIZE_KB
   796                              <1> WinSize9: 		dw	VBE_DISPI_BANK_SIZE_KB
   797                              <1> WinASegment9:		dw	VGAMEM_GRAPH
   798                              <1> WinBSegment9:		dw	0000h
   799                              <1> WinFuncPtr9:		dd	0
   800                              <1> BytesPerScanLine9:	dw	1600
   801                              <1> XResolution9:		dw	800
   802                              <1> YResolution9:		dw	600
   803                              <1> XCharSize9:		db	8
   804                              <1> YCharSize9:		db	16
   805                              <1> NumberOfPlanes9:	db	1
   806                              <1> BitsPerPixel9:		db	16
   807                              <1> NumberOfBanks9:		db	15
   808                              <1> MemoryModel9:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   809                              <1> BankSize9:		db	0
   810                              <1> NumberOfImagePages9:	db	16
   811                              <1> Reserved_page9:		db	0
   812                              <1> RedMaskSize9:		db	5
   813                              <1> RedFieldPosition9:	db	11
   814                              <1> GreenMaskSize9:		db	6
   815                              <1> GreenFieldPosition9:	db	5
   816                              <1> BlueMaskSize9:		db	5
   817                              <1> BlueFieldPosition9:	db	0
   818                              <1> RsvdMaskSize9:		db	0
   819                              <1> RsvdFieldPosition9:	db	0
   820                              <1> DirectColorModeInfo9:	db	0
   821                              <1> PhysBasePtr9:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   822                              <1> OffScreenMemOffset9:	dd	0
   823                              <1> OffScreenMemSize9:	dw	0
   824                              <1> LinBytesPerScanLine9:	dw	1600
   825                              <1> BnkNumberOfPages9: 	db	0
   826                              <1> LinNumberOfPages9: 	db	0
   827                              <1> LinRedMaskSize9:	db	5
   828                              <1> LinRedFieldPosition9:	db	11
   829                              <1> LinGreenMaskSize9:	db	6
   830                              <1> LinGreenFieldPosition9:	db	5
   831                              <1> LinBlueMaskSize9:	db	5
   832                              <1> LinBlueFieldPosition9:	db	0
   833                              <1> LinRsvdMaskSize9:	db	0
   834                              <1> LinRsvdFieldPosition9:	db	0
   835                              <1> MaxPixelClock9:		dd	0
   836                              <1> 	
   837                              <1> 			dw	0115h ; 800x600x24
   838                              <1> ModeAttributes10: 	dw	MODE_ATTRIBUTES
   839                              <1> WinAAttributes10: 	db	WINA_ATTRIBUTES
   840                              <1> WinBAttributes10: 	db	0
   841                              <1> WinGranularity10: 	dw	VBE_DISPI_BANK_SIZE_KB
   842                              <1> WinSize10: 		dw	VBE_DISPI_BANK_SIZE_KB
   843                              <1> WinASegment10:		dw	VGAMEM_GRAPH
   844                              <1> WinBSegment10:		dw	0000h
   845                              <1> WinFuncPtr10:		dd	0
   846                              <1> BytesPerScanLine10:	dw	2400
   847                              <1> XResolution10:		dw	800
   848                              <1> YResolution10:		dw	600
   849                              <1> XCharSize10:		db	8
   850                              <1> YCharSize10:		db	16
   851                              <1> NumberOfPlanes10:	db	1
   852                              <1> BitsPerPixel10:		db	24
   853                              <1> NumberOfBanks10:	db	22
   854                              <1> MemoryModel10:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   855                              <1> BankSize10:		db	0
   856                              <1> NumberOfImagePages10:	db	10
   857                              <1> Reserved_page10:	db	0
   858                              <1> RedMaskSize10:		db	8
   859                              <1> RedFieldPosition10:	db	16
   860                              <1> GreenMaskSize10:	db	8
   861                              <1> GreenFieldPosition10:	db	8
   862                              <1> BlueMaskSize10:		db	8
   863                              <1> BlueFieldPosition10:	db	0
   864                              <1> RsvdMaskSize10:		db	0
   865                              <1> RsvdFieldPosition10:	db	0
   866                              <1> DirectColorModeInfo10:	db	0
   867                              <1> PhysBasePtr10:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   868                              <1> OffScreenMemOffset10:	dd	0
   869                              <1> OffScreenMemSize10:	dw	0
   870                              <1> LinBytesPerScanLine10:	dw	2400
   871                              <1> BnkNumberOfPages10: 	db	0
   872                              <1> LinNumberOfPages10: 	db	0
   873                              <1> LinRedMaskSize10:	db	8
   874                              <1> LinRedFieldPosition10:	db	16
   875                              <1> LinGreenMaskSize10:	db	8
   876                              <1> LinGreenFieldPosition10:db	8
   877                              <1> LinBlueMaskSize10:	db	8
   878                              <1> LinBlueFieldPosition10:	db	0
   879                              <1> LinRsvdMaskSize10:	db	0
   880                              <1> LinRsvdFieldPosition10:	db	0
   881                              <1> MaxPixelClock10:	dd	0
   882                              <1> 
   883                              <1> 			dw	0117h ; 1024x768x16
   884                              <1> ModeAttributes11: 	dw	MODE_ATTRIBUTES
   885                              <1> WinAAttributes11: 	db	WINA_ATTRIBUTES
   886                              <1> WinBAttributes11: 	db	0
   887                              <1> WinGranularity11: 	dw	VBE_DISPI_BANK_SIZE_KB
   888                              <1> WinSize11: 		dw	VBE_DISPI_BANK_SIZE_KB
   889                              <1> WinASegment11:		dw	VGAMEM_GRAPH
   890                              <1> WinBSegment11:		dw	0000h
   891                              <1> WinFuncPtr11:		dd	0
   892                              <1> BytesPerScanLine11:	dw	2048
   893                              <1> XResolution11:		dw	1024
   894                              <1> YResolution11:		dw	768
   895                              <1> XCharSize11:		db	8
   896                              <1> YCharSize11:		db	16
   897                              <1> NumberOfPlanes11:	db	1
   898                              <1> BitsPerPixel11:		db	16
   899                              <1> NumberOfBanks11:	db	24
   900                              <1> MemoryModel11:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   901                              <1> BankSize11:		db	0
   902                              <1> NumberOfImagePages11:	db	9
   903                              <1> Reserved_page11:	db	0
   904                              <1> RedMaskSize11:		db	5
   905                              <1> RedFieldPosition11:	db	11
   906                              <1> GreenMaskSize11:	db	6
   907                              <1> GreenFieldPosition11:	db	5
   908                              <1> BlueMaskSize11:		db	5
   909                              <1> BlueFieldPosition11:	db	0
   910                              <1> RsvdMaskSize11:		db	0
   911                              <1> RsvdFieldPosition11:	db	0
   912                              <1> DirectColorModeInfo11:	db	0
   913                              <1> PhysBasePtr11:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS,
   914                              <1> OffScreenMemOffset11:	dd	0
   915                              <1> OffScreenMemSize11:	dw	0
   916                              <1> LinBytesPerScanLine11:	dw	2048
   917                              <1> BnkNumberOfPages11: 	db	0
   918                              <1> LinNumberOfPages11: 	db	0
   919                              <1> LinRedMaskSize11:	db	5
   920                              <1> LinRedFieldPosition11:	db	11
   921                              <1> LinGreenMaskSize11:	db	6
   922                              <1> LinGreenFieldPosition11:db	5
   923                              <1> LinBlueMaskSize11:	db	5
   924                              <1> LinBlueFieldPosition11:	db	0
   925                              <1> LinRsvdMaskSize11:	db	0
   926                              <1> LinRsvdFieldPosition11:	db	0
   927                              <1> MaxPixelClock11:	dd	0
   928                              <1> 
   929                              <1> 			dw	0118h ; 1024x768x24
   930                              <1> ModeAttributes12: 	dw	MODE_ATTRIBUTES
   931                              <1> WinAAttributes12: 	db	WINA_ATTRIBUTES
   932                              <1> WinBAttributes12: 	db	0
   933                              <1> WinGranularity12: 	dw	VBE_DISPI_BANK_SIZE_KB
   934                              <1> WinSize12: 		dw	VBE_DISPI_BANK_SIZE_KB
   935                              <1> WinASegment12:		dw	VGAMEM_GRAPH
   936                              <1> WinBSegment12:		dw	0000h
   937                              <1> WinFuncPtr12:		dd	0
   938                              <1> BytesPerScanLine12:	dw	3072
   939                              <1> XResolution12:		dw	1024
   940                              <1> YResolution12:		dw	768
   941                              <1> XCharSize12:		db	8
   942                              <1> YCharSize12:		db	16
   943                              <1> NumberOfPlanes12:	db	1
   944                              <1> BitsPerPixel12:		db	24
   945                              <1> NumberOfBanks12:	db	36
   946                              <1> MemoryModel12:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   947                              <1> BankSize12:		db	0
   948                              <1> NumberOfImagePages12:	db	6
   949                              <1> Reserved_page12:	db	0
   950                              <1> RedMaskSize12:		db	8
   951                              <1> RedFieldPosition12:	db	16
   952                              <1> GreenMaskSize12:	db	8
   953                              <1> GreenFieldPosition12:	db	8
   954                              <1> BlueMaskSize12:		db	8
   955                              <1> BlueFieldPosition12:	db	0
   956                              <1> RsvdMaskSize12:		db	0
   957                              <1> RsvdFieldPosition12:	db	0
   958                              <1> DirectColorModeInfo12:	db	0
   959                              <1> PhysBasePtr12:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
   960                              <1> OffScreenMemOffset12:	dd	0
   961                              <1> OffScreenMemSize12:	dw	0
   962                              <1> LinBytesPerScanLine12:	dw	3072
   963                              <1> BnkNumberOfPages12: 	db	0
   964                              <1> LinNumberOfPages12: 	db	0
   965                              <1> LinRedMaskSize12:	db	8
   966                              <1> LinRedFieldPosition12:	db	16
   967                              <1> LinGreenMaskSize12:	db	8
   968                              <1> LinGreenFieldPosition12:db	8
   969                              <1> LinBlueMaskSize12:	db	8
   970                              <1> LinBlueFieldPosition12:	db	0
   971                              <1> LinRsvdMaskSize12:	db	0
   972                              <1> LinRsvdFieldPosition12:	db	0
   973                              <1> MaxPixelClock12:	dd	0
   974                              <1> 
   975                              <1> 			dw	0140h ; 320x200x32
   976                              <1> ModeAttributes13: 	dw	MODE_ATTRIBUTES
   977                              <1> WinAAttributes13: 	db	WINA_ATTRIBUTES
   978                              <1> WinBAttributes13: 	db	0
   979                              <1> WinGranularity13: 	dw	VBE_DISPI_BANK_SIZE_KB
   980                              <1> WinSize13: 		dw	VBE_DISPI_BANK_SIZE_KB
   981                              <1> WinASegment13:		dw	VGAMEM_GRAPH
   982                              <1> WinBSegment13:		dw	0000h
   983                              <1> WinFuncPtr13:		dd	0
   984                              <1> BytesPerScanLine13:	dw	1280
   985                              <1> XResolution13:		dw	320
   986                              <1> YResolution13:		dw	200
   987                              <1> XCharSize13:		db	8
   988                              <1> YCharSize13:		db	16
   989                              <1> NumberOfPlanes13:	db	1
   990                              <1> BitsPerPixel13:		db	32
   991                              <1> NumberOfBanks13:	db	4
   992                              <1> MemoryModel13:		db	VBE_MEMORYMODEL_DIRECT_COLOR
   993                              <1> BankSize13:		db	0
   994                              <1> NumberOfImagePages13:	db	64
   995                              <1> Reserved_page13:	db	0
   996                              <1> RedMaskSize13:		db	8
   997                              <1> RedFieldPosition13:	db	16
   998                              <1> GreenMaskSize13:	db	8
   999                              <1> GreenFieldPosition13:	db	8
  1000                              <1> BlueMaskSize13:		db	8
  1001                              <1> BlueFieldPosition13:	db	0
  1002                              <1> RsvdMaskSize13:		db	8
  1003                              <1> RsvdFieldPosition13:	db	24
  1004                              <1> DirectColorModeInfo13:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  1005                              <1> PhysBasePtr13:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1006                              <1> OffScreenMemOffset13:	dd	0
  1007                              <1> OffScreenMemSize13:	dw	0
  1008                              <1> LinBytesPerScanLine13:	dw	1280
  1009                              <1> BnkNumberOfPages13: 	db	0
  1010                              <1> LinNumberOfPages13: 	db	0
  1011                              <1> LinRedMaskSize13:	db	8
  1012                              <1> LinRedFieldPosition13:	db	16
  1013                              <1> LinGreenMaskSize13:	db	8
  1014                              <1> LinGreenFieldPosition13:db	8
  1015                              <1> LinBlueMaskSize13:	db	8
  1016                              <1> LinBlueFieldPosition13:	db	0
  1017                              <1> LinRsvdMaskSize13:	db	8
  1018                              <1> LinRsvdFieldPosition13:	db	24
  1019                              <1> MaxPixelClock13:	dd	0
  1020                              <1> 
  1021                              <1> 			dw	0141h ; 640x400x32
  1022                              <1> ModeAttributes14: 	dw	MODE_ATTRIBUTES
  1023                              <1> WinAAttributes14: 	db	WINA_ATTRIBUTES
  1024                              <1> WinBAttributes14: 	db	0
  1025                              <1> WinGranularity14: 	dw	VBE_DISPI_BANK_SIZE_KB
  1026                              <1> WinSize14: 		dw	VBE_DISPI_BANK_SIZE_KB
  1027                              <1> WinASegment14:		dw	VGAMEM_GRAPH
  1028                              <1> WinBSegment14:		dw	0000h
  1029                              <1> WinFuncPtr14:		dd	0
  1030                              <1> BytesPerScanLine14:	dw	2560
  1031                              <1> XResolution14:		dw	640
  1032                              <1> YResolution14:		dw	400
  1033                              <1> XCharSize14:		db	8
  1034                              <1> YCharSize14:		db	16
  1035                              <1> NumberOfPlanes14:	db	1
  1036                              <1> BitsPerPixel14:		db	32
  1037                              <1> NumberOfBanks14:	db	16
  1038                              <1> MemoryModel14:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1039                              <1> BankSize14:		db	0
  1040                              <1> NumberOfImagePages14:	db	15
  1041                              <1> Reserved_page14:	db	0
  1042                              <1> RedMaskSize14:		db	8
  1043                              <1> RedFieldPosition14:	db	16
  1044                              <1> GreenMaskSize14:	db	8
  1045                              <1> GreenFieldPosition14:	db	8
  1046                              <1> BlueMaskSize14:		db	8
  1047                              <1> BlueFieldPosition14:	db	0
  1048                              <1> RsvdMaskSize14:		db	8
  1049                              <1> RsvdFieldPosition14:	db	24
  1050                              <1> DirectColorModeInfo14:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  1051                              <1> PhysBasePtr14:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1052                              <1> OffScreenMemOffset14:	dd  	0
  1053                              <1> OffScreenMemSize14:	dw	0
  1054                              <1> LinBytesPerScanLine14:	dw	2560
  1055                              <1> BnkNumberOfPages14: 	db	0
  1056                              <1> LinNumberOfPages14: 	db	0
  1057                              <1> LinRedMaskSize14:	db	8
  1058                              <1> LinRedFieldPosition14:	db	16
  1059                              <1> LinGreenMaskSize14:	db	8
  1060                              <1> LinGreenFieldPosition14:db	8
  1061                              <1> LinBlueMaskSize14:	db	8
  1062                              <1> LinBlueFieldPosition14:	db	0
  1063                              <1> LinRsvdMaskSize14:	db	8
  1064                              <1> LinRsvdFieldPosition14:	db	24
  1065                              <1> MaxPixelClock14:	dd	0
  1066                              <1> 
  1067                              <1> 			dw	0142 ; 640x480x32
  1068                              <1> ModeAttributes15: 	dw	MODE_ATTRIBUTES
  1069                              <1> WinAAttributes15: 	db	WINA_ATTRIBUTES
  1070                              <1> WinBAttributes15: 	db	0
  1071                              <1> WinGranularity15: 	dw	VBE_DISPI_BANK_SIZE_KB
  1072                              <1> WinSize15: 		dw	VBE_DISPI_BANK_SIZE_KB
  1073                              <1> WinASegment15:		dw	VGAMEM_GRAPH
  1074                              <1> WinBSegment15:		dw	0000h
  1075                              <1> WinFuncPtr15:		dd	0
  1076                              <1> BytesPerScanLine15:	dw	2560
  1077                              <1> XResolution15:		dw	640
  1078                              <1> YResolution15:		dw	480
  1079                              <1> XCharSize15:		db	8
  1080                              <1> YCharSize15:		db	16
  1081                              <1> NumberOfPlanes15:	db	1
  1082                              <1> BitsPerPixel15:		db	32
  1083                              <1> NumberOfBanks15:	db	19
  1084                              <1> MemoryModel15:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1085                              <1> BankSize15:		db	0
  1086                              <1> NumberOfImagePages15:	db	12
  1087                              <1> Reserved_page15:	db	0
  1088                              <1> RedMaskSize15:		db	8
  1089                              <1> RedFieldPosition15:	db	16
  1090                              <1> GreenMaskSize15:	db	8
  1091                              <1> GreenFieldPosition15:	db	8
  1092                              <1> BlueMaskSize15:		db	8
  1093                              <1> BlueFieldPosition15:	db	0
  1094                              <1> RsvdMaskSize15:		db	8
  1095                              <1> RsvdFieldPosition15:	db	24
  1096                              <1> DirectColorModeInfo15:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE,
  1097                              <1> PhysBasePtr15:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS,
  1098                              <1> OffScreenMemOffset15:	dd	0
  1099                              <1> OffScreenMemSize15:	dw	0
  1100                              <1> LinBytesPerScanLine15:	dw	2560
  1101                              <1> BnkNumberOfPages15: 	db	0
  1102                              <1> LinNumberOfPages15: 	db	0
  1103                              <1> LinRedMaskSize15:	db	8
  1104                              <1> LinRedFieldPosition15:	db	16
  1105                              <1> LinGreenMaskSize15:	db	8
  1106                              <1> LinGreenFieldPosition15:db	8
  1107                              <1> LinBlueMaskSize15:	db	8
  1108                              <1> LinBlueFieldPosition15:	db	0
  1109                              <1> LinRsvdMaskSize15:	db	8
  1110                              <1> LinRsvdFieldPosition15:	db	24
  1111                              <1> MaxPixelClock15:	dd	0
  1112                              <1> 
  1113                              <1> 			dw	0143h ; 800x600x32
  1114                              <1> ModeAttributes16: 	dw	MODE_ATTRIBUTES
  1115                              <1> WinAAttributes16: 	db	WINA_ATTRIBUTES
  1116                              <1> WinBAttributes16: 	db	0
  1117                              <1> WinGranularity16: 	dw	VBE_DISPI_BANK_SIZE_KB
  1118                              <1> WinSize16: 		dw	VBE_DISPI_BANK_SIZE_KB
  1119                              <1> WinASegment16:		dw	VGAMEM_GRAPH
  1120                              <1> WinBSegment16:		dw	0000h
  1121                              <1> WinFuncPtr16:		dd	0
  1122                              <1> BytesPerScanLine16:	dw	3200
  1123                              <1> XResolution16:		dw	800
  1124                              <1> YResolution16:		dw	600
  1125                              <1> XCharSize16:		db	8
  1126                              <1> YCharSize16:		db	16
  1127                              <1> NumberOfPlanes16:	db	1
  1128                              <1> BitsPerPixel16:		db	32
  1129                              <1> NumberOfBanks16:	db	30
  1130                              <1> MemoryModel16:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1131                              <1> BankSize16:		db	0
  1132                              <1> NumberOfImagePages16:	db	7
  1133                              <1> Reserved_page16:	db	0
  1134                              <1> RedMaskSize16:		db	8
  1135                              <1> RedFieldPosition16:	db	16
  1136                              <1> GreenMaskSize16:	db	8
  1137                              <1> GreenFieldPosition16:	db	8
  1138                              <1> BlueMaskSize16:		db	8
  1139                              <1> BlueFieldPosition16:	db	0
  1140                              <1> RsvdMaskSize16:		db	8
  1141                              <1> RsvdFieldPosition16:	db	24
  1142                              <1> DirectColorModeInfo16:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE,
  1143                              <1> PhysBasePtr16:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS,
  1144                              <1> OffScreenMemOffset16:	dd	0
  1145                              <1> OffScreenMemSize16:	dw	0
  1146                              <1> LinBytesPerScanLine16:	dw	3200
  1147                              <1> BnkNumberOfPages16: 	db	0
  1148                              <1> LinNumberOfPages16: 	db	0
  1149                              <1> LinRedMaskSize16:	db	8
  1150                              <1> LinRedFieldPosition16:	db	16
  1151                              <1> LinGreenMaskSize16:	db	8
  1152                              <1> LinGreenFieldPosition16:db	8
  1153                              <1> LinBlueMaskSize16:	db	8
  1154                              <1> LinBlueFieldPosition16:	db	0
  1155                              <1> LinRsvdMaskSize16:	db	8
  1156                              <1> LinRsvdFieldPosition16:	db	24
  1157                              <1> MaxPixelClock16:	dd	0
  1158                              <1> 	
  1159                              <1> 			dw	0144h ; 1024x768x32
  1160                              <1> ModeAttributes17: 	dw	MODE_ATTRIBUTES
  1161                              <1> WinAAttributes17: 	db	WINA_ATTRIBUTES
  1162                              <1> WinBAttributes17: 	db	0
  1163                              <1> WinGranularity17: 	dw	VBE_DISPI_BANK_SIZE_KB
  1164                              <1> WinSize17: 		dw	VBE_DISPI_BANK_SIZE_KB
  1165                              <1> WinASegment17:		dw	VGAMEM_GRAPH
  1166                              <1> WinBSegment17:		dw	0000h
  1167                              <1> WinFuncPtr17:		dd	0
  1168                              <1> BytesPerScanLine17:	dw	4096
  1169                              <1> XResolution17:		dw	1024
  1170                              <1> YResolution17:		dw	768
  1171                              <1> XCharSize17:		db	8
  1172                              <1> YCharSize17:		db	16
  1173                              <1> NumberOfPlanes17:	db	1
  1174                              <1> BitsPerPixel17:		db	32
  1175                              <1> NumberOfBanks17:	db	48
  1176                              <1> MemoryModel17:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1177                              <1> BankSize17:		db	0
  1178                              <1> NumberOfImagePages17:	db	4
  1179                              <1> Reserved_page17:	db	0
  1180                              <1> RedMaskSize17:		db	8
  1181                              <1> RedFieldPosition17:	db	16
  1182                              <1> GreenMaskSize17:	db	8
  1183                              <1> GreenFieldPosition17:	db	8
  1184                              <1> BlueMaskSize17:		db	8
  1185                              <1> BlueFieldPosition17:	db	0
  1186                              <1> RsvdMaskSize17:		db	8
  1187                              <1> RsvdFieldPosition17:	db	24
  1188                              <1> DirectColorModeInfo17:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  1189                              <1> PhysBasePtr17:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1190                              <1> OffScreenMemOffset17:	dd	0
  1191                              <1> OffScreenMemSize17:	dw	0
  1192                              <1> LinBytesPerScanLine17:	dw	4096
  1193                              <1> BnkNumberOfPages17: 	db	0
  1194                              <1> LinNumberOfPages17: 	db	0
  1195                              <1> LinRedMaskSize17:	db	8
  1196                              <1> LinRedFieldPosition17:	db	16
  1197                              <1> LinGreenMaskSize17:	db	8
  1198                              <1> LinGreenFieldPosition17:db	8
  1199                              <1> LinBlueMaskSize17:	db	8
  1200                              <1> LinBlueFieldPosition17:	db	0
  1201                              <1> LinRsvdMaskSize17:	db	8
  1202                              <1> LinRsvdFieldPosition17:	db	24
  1203                              <1> MaxPixelClock17:	dd	0
  1204                              <1> 	
  1205                              <1> 			dw	0146h ; 320x200x8
  1206                              <1> ModeAttributes18: 	dw	MODE_ATTRIBUTES
  1207                              <1> WinAAttributes18: 	db	WINA_ATTRIBUTES
  1208                              <1> WinBAttributes18: 	db	0
  1209                              <1> WinGranularity18: 	dw	VBE_DISPI_BANK_SIZE_KB
  1210                              <1> WinSize18: 		dw	VBE_DISPI_BANK_SIZE_KB
  1211                              <1> WinASegment18:		dw	VGAMEM_GRAPH
  1212                              <1> WinBSegment18:		dw	0000h
  1213                              <1> WinFuncPtr18:		dd	0
  1214                              <1> BytesPerScanLine18:	dw	320
  1215                              <1> XResolution18:		dw	320
  1216                              <1> YResolution18:		dw	200
  1217                              <1> XCharSize18:		db	8
  1218                              <1> YCharSize18:		db	16
  1219                              <1> NumberOfPlanes18:	db	1
  1220                              <1> BitsPerPixel18:		db	8
  1221                              <1> NumberOfBanks18:	db	1
  1222                              <1> MemoryModel18:		db	VBE_MEMORYMODEL_PACKED_PIXEL
  1223                              <1> BankSize18:		db	0
  1224                              <1> NumberOfImagePages18:	db	255 ; 261 in vbetables.h (03/01/2020) !
  1225                              <1> Reserved_page18:	db	0
  1226                              <1> RedMaskSize18:		db	0
  1227                              <1> RedFieldPosition18:	db	0
  1228                              <1> GreenMaskSize18:	db	0
  1229                              <1> GreenFieldPosition18:	db	0
  1230                              <1> BlueMaskSize18:		db	0
  1231                              <1> BlueFieldPosition18:	db	0
  1232                              <1> RsvdMaskSize18:		db	0
  1233                              <1> RsvdFieldPosition18:	db	0
  1234                              <1> DirectColorModeInfo18:	db	0
  1235                              <1> PhysBasePtr18:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1236                              <1> OffScreenMemOffset18:	dd	0
  1237                              <1> OffScreenMemSize18:	dw	0
  1238                              <1> LinBytesPerScanLine18:	dw	320
  1239                              <1> BnkNumberOfPages18: 	db	0
  1240                              <1> LinNumberOfPages18: 	db	0
  1241                              <1> LinRedMaskSize18:	db	0
  1242                              <1> LinRedFieldPosition18: 	db	0
  1243                              <1> LinGreenMaskSize18: 	db	0
  1244                              <1> LinGreenFieldPosition18:db	0
  1245                              <1> LinBlueMaskSize18: 	db	0
  1246                              <1> LinBlueFieldPosition18: db	0
  1247                              <1> LinRsvdMaskSize18: 	db	0
  1248                              <1> LinRsvdFieldPosition18: db	0
  1249                              <1> MaxPixelClock18:	dd	0
  1250                              <1> 
  1251                              <1> 			dw	018Dh ; 1280x720x16
  1252                              <1> ModeAttributes19: 	dw	MODE_ATTRIBUTES
  1253                              <1> WinAAttributes19: 	db	WINA_ATTRIBUTES
  1254                              <1> WinBAttributes19: 	db	0
  1255                              <1> WinGranularity19: 	dw	VBE_DISPI_BANK_SIZE_KB
  1256                              <1> WinSize19: 		dw	VBE_DISPI_BANK_SIZE_KB
  1257                              <1> WinASegment19:		dw	VGAMEM_GRAPH
  1258                              <1> WinBSegment19:		dw	0000h
  1259                              <1> WinFuncPtr19:		dd	0
  1260                              <1> BytesPerScanLine19:	dw	2560
  1261                              <1> XResolution19:		dw	1280
  1262                              <1> YResolution19:		dw	720
  1263                              <1> XCharSize19:		db	8
  1264                              <1> YCharSize19:		db	16
  1265                              <1> NumberOfPlanes19:	db	1
  1266                              <1> BitsPerPixel19:		db	16
  1267                              <1> NumberOfBanks19:	db	29
  1268                              <1> MemoryModel19:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1269                              <1> BankSize19:		db	0
  1270                              <1> NumberOfImagePages19:	db	8
  1271                              <1> Reserved_page19:	db	0
  1272                              <1> RedMaskSize19:		db	5
  1273                              <1> RedFieldPosition19:	db	11
  1274                              <1> GreenMaskSize19:	db	6
  1275                              <1> GreenFieldPosition19:	db	5
  1276                              <1> BlueMaskSize19:		db	5
  1277                              <1> BlueFieldPosition19:	db	0
  1278                              <1> RsvdMaskSize19:		db	0
  1279                              <1> RsvdFieldPosition19:	db	0
  1280                              <1> DirectColorModeInfo19:	db	0
  1281                              <1> PhysBasePtr19:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1282                              <1> OffScreenMemOffset19:	dd	0
  1283                              <1> OffScreenMemSize19:	dw	0
  1284                              <1> LinBytesPerScanLine19:	dw	2560
  1285                              <1> BnkNumberOfPages19: 	db	0
  1286                              <1> LinNumberOfPages19: 	db	0
  1287                              <1> LinRedMaskSize19:	db	5
  1288                              <1> LinRedFieldPosition19:	db	11
  1289                              <1> LinGreenMaskSize19:	db	6
  1290                              <1> LinGreenFieldPosition19:db	5
  1291                              <1> LinBlueMaskSize19:	db	5
  1292                              <1> LinBlueFieldPosition19:	db	0
  1293                              <1> LinRsvdMaskSize19:	db	0
  1294                              <1> LinRsvdFieldPosition19:	db	0
  1295                              <1> MaxPixelClock19:	dd	0
  1296                              <1> 
  1297                              <1> 			dw	018Eh ; 1280x720x24
  1298                              <1> ModeAttributes20: 	dw	MODE_ATTRIBUTES
  1299                              <1> WinAAttributes20: 	db	WINA_ATTRIBUTES
  1300                              <1> WinBAttributes20: 	db	0
  1301                              <1> WinGranularity20: 	dw	VBE_DISPI_BANK_SIZE_KB
  1302                              <1> WinSize20: 		dw	VBE_DISPI_BANK_SIZE_KB
  1303                              <1> WinASegment20:		dw	VGAMEM_GRAPH
  1304                              <1> WinBSegment20:		dw	0000h
  1305                              <1> WinFuncPtr20:		dd	0
  1306                              <1> BytesPerScanLine20:	dw	3840
  1307                              <1> XResolution20:		dw	1280
  1308                              <1> YResolution20:		dw	720
  1309                              <1> XCharSize20:		db	8
  1310                              <1> YCharSize20:		db	16
  1311                              <1> NumberOfPlanes20:	db	1
  1312                              <1> BitsPerPixel20:		db	24
  1313                              <1> NumberOfBanks20:	db	43
  1314                              <1> MemoryModel20:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1315                              <1> BankSize20:		db	0
  1316                              <1> NumberOfImagePages20:	db	5
  1317                              <1> Reserved_page20:	db	0
  1318                              <1> RedMaskSize20:		db	8
  1319                              <1> RedFieldPosition20:	db	16
  1320                              <1> GreenMaskSize20:	db	8
  1321                              <1> GreenFieldPosition20:	db	8
  1322                              <1> BlueMaskSize20:		db	8
  1323                              <1> BlueFieldPosition20:	db	0
  1324                              <1> RsvdMaskSize20:		db	0
  1325                              <1> RsvdFieldPosition20:	db	0
  1326                              <1> DirectColorModeInfo20:	db	0
  1327                              <1> PhysBasePtr20:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1328                              <1> OffScreenMemOffset20:	dd	0
  1329                              <1> OffScreenMemSize20:	dw	0
  1330                              <1> LinBytesPerScanLine20:	dw	3840
  1331                              <1> BnkNumberOfPages20: 	db	0
  1332                              <1> LinNumberOfPages20: 	db	0
  1333                              <1> LinRedMaskSize20:	db	8
  1334                              <1> LinRedFieldPosition20:	db	16
  1335                              <1> LinGreenMaskSize20:	db	8
  1336                              <1> LinGreenFieldPosition20:db	8
  1337                              <1> LinBlueMaskSize20:	db	8
  1338                              <1> LinBlueFieldPosition20:	db	0
  1339                              <1> LinRsvdMaskSize20:	db	0
  1340                              <1> LinRsvdFieldPosition20:	db	0
  1341                              <1> MaxPixelClock20:	dd	0
  1342                              <1> 	
  1343                              <1> 			dw	018Fh ; 1280x720x32
  1344                              <1> ModeAttributes21: 	dw	MODE_ATTRIBUTES
  1345                              <1> WinAAttributes21: 	db	WINA_ATTRIBUTES
  1346                              <1> WinBAttributes21: 	db	0
  1347                              <1> WinGranularity21: 	dw	VBE_DISPI_BANK_SIZE_KB
  1348                              <1> WinSize21: 		dw	VBE_DISPI_BANK_SIZE_KB
  1349                              <1> WinASegment21:		dw	VGAMEM_GRAPH
  1350                              <1> WinBSegment21:		dw	0000h
  1351                              <1> WinFuncPtr21:		dd	0
  1352                              <1> BytesPerScanLine21:	dw	5120
  1353                              <1> XResolution21:		dw	1280
  1354                              <1> YResolution21:		dw	720
  1355                              <1> XCharSize21:		db	8
  1356                              <1> YCharSize21:		db	16
  1357                              <1> NumberOfPlanes21:	db	1
  1358                              <1> BitsPerPixel21:		db	32
  1359                              <1> NumberOfBanks21:	db	57
  1360                              <1> MemoryModel21:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1361                              <1> BankSize21:		db	0
  1362                              <1> NumberOfImagePages21:	db	3
  1363                              <1> Reserved_page21:	db	0
  1364                              <1> RedMaskSize21:		db	8
  1365                              <1> RedFieldPosition21:	db	16
  1366                              <1> GreenMaskSize21:	db	8
  1367                              <1> GreenFieldPosition21:	db	8
  1368                              <1> BlueMaskSize21:		db	8
  1369                              <1> BlueFieldPosition21:	db	0
  1370                              <1> RsvdMaskSize21:		db	8
  1371                              <1> RsvdFieldPosition21:	db	24
  1372                              <1> DirectColorModeInfo21:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  1373                              <1> PhysBasePtr21:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1374                              <1> OffScreenMemOffset21:	dd	0
  1375                              <1> OffScreenMemSize21:	dw	0
  1376                              <1> LinBytesPerScanLine21:	dw	5120
  1377                              <1> BnkNumberOfPages21: 	db	0
  1378                              <1> LinNumberOfPages21: 	db	0
  1379                              <1> LinRedMaskSize21:	db	8
  1380                              <1> LinRedFieldPosition21:	db	16
  1381                              <1> LinGreenMaskSize21:	db	8
  1382                              <1> LinGreenFieldPosition21:db	8
  1383                              <1> LinBlueMaskSize21:	db	8
  1384                              <1> LinBlueFieldPosition21:	db	0
  1385                              <1> LinRsvdMaskSize21:	db	8
  1386                              <1> LinRsvdFieldPosition21:	db	24
  1387                              <1> MaxPixelClock21:	dd	0
  1388                              <1> 			
  1389                              <1> 			dw	0190h ; 1920x1080x16
  1390                              <1> ModeAttributes22: 	dw	MODE_ATTRIBUTES
  1391                              <1> WinAAttributes22: 	db	WINA_ATTRIBUTES
  1392                              <1> WinBAttributes22: 	db	0
  1393                              <1> WinGranularity22: 	dw	VBE_DISPI_BANK_SIZE_KB
  1394                              <1> WinSize22: 		dw	VBE_DISPI_BANK_SIZE_KB
  1395                              <1> WinASegment22:		dw	VGAMEM_GRAPH
  1396                              <1> WinBSegment22:		dw	0000h
  1397                              <1> WinFuncPtr22:		dd	0
  1398                              <1> BytesPerScanLine22:	dw	3840
  1399                              <1> XResolution22:		dw	1920
  1400                              <1> YResolution22:		dw	1080
  1401                              <1> XCharSize22:		db	8
  1402                              <1> YCharSize22:		db	16
  1403                              <1> NumberOfPlanes22:	db	1
  1404                              <1> BitsPerPixel22:		db	16
  1405                              <1> NumberOfBanks22:	db	64
  1406                              <1> MemoryModel22:		db	VBE_MEMORYMODEL_DIRECT_COLOR,
  1407                              <1> BankSize22:		db	0
  1408                              <1> NumberOfImagePages22:	db	3
  1409                              <1> Reserved_page22:	db	0
  1410                              <1> RedMaskSize22:		db	5
  1411                              <1> RedFieldPosition22:	db	11
  1412                              <1> GreenMaskSize22:	db	6
  1413                              <1> GreenFieldPosition22:	db	5
  1414                              <1> BlueMaskSize22:		db	5
  1415                              <1> BlueFieldPosition22:	db	0
  1416                              <1> RsvdMaskSize22:		db	0
  1417                              <1> RsvdFieldPosition22:	db	0
  1418                              <1> DirectColorModeInfo22:	db	0
  1419                              <1> PhysBasePtr22:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1420                              <1> OffScreenMemOffset22:	dd	0
  1421                              <1> OffScreenMemSize22:	dw	0
  1422                              <1> LinBytesPerScanLine22:	dw	3840
  1423                              <1> BnkNumberOfPages22: 	db	0
  1424                              <1> LinNumberOfPages22: 	db	0
  1425                              <1> LinRedMaskSize22:	db	5
  1426                              <1> LinRedFieldPosition22:	db	11
  1427                              <1> LinGreenMaskSize22:	db	6
  1428                              <1> LinGreenFieldPosition22:db	5
  1429                              <1> LinBlueMaskSize22:	db	5
  1430                              <1> LinBlueFieldPosition22:	db	0
  1431                              <1> LinRsvdMaskSize22:	db	0
  1432                              <1> LinRsvdFieldPosition22:	db	0
  1433                              <1> MaxPixelClock22:	dd	0
  1434                              <1> 			
  1435                              <1> 			dw	0191h ; 1920x1080x24
  1436                              <1> ModeAttributes23: 	dw	MODE_ATTRIBUTES
  1437                              <1> WinAAttributes23: 	db	WINA_ATTRIBUTES
  1438                              <1> WinBAttributes23: 	db	0
  1439                              <1> WinGranularity23: 	dw	VBE_DISPI_BANK_SIZE_KB
  1440                              <1> WinSize23: 		dw	VBE_DISPI_BANK_SIZE_KB
  1441                              <1> WinASegment23:		dw	VGAMEM_GRAPH
  1442                              <1> WinBSegment23:		dw	0000h
  1443                              <1> WinFuncPtr23:		dd	0
  1444                              <1> BytesPerScanLine23:	dw	5760
  1445                              <1> XResolution23:		dw	1920
  1446                              <1> YResolution23:		dw	1080
  1447                              <1> XCharSize23:		db	8
  1448                              <1> YCharSize23:		db	16
  1449                              <1> NumberOfPlanes23:	db	1
  1450                              <1> BitsPerPixel23:		db	24
  1451                              <1> NumberOfBanks23:	db	95
  1452                              <1> MemoryModel23:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1453                              <1> BankSize23:		db	0
  1454                              <1> NumberOfImagePages23:	db	1
  1455                              <1> Reserved_page23:	db	0
  1456                              <1> RedMaskSize23:		db	8
  1457                              <1> RedFieldPosition23:	db	16
  1458                              <1> GreenMaskSize23:	db	8
  1459                              <1> GreenFieldPosition23:	db	8
  1460                              <1> BlueMaskSize23:		db	8
  1461                              <1> BlueFieldPosition23:	db	0
  1462                              <1> RsvdMaskSize23:		db	0
  1463                              <1> RsvdFieldPosition23:	db	0
  1464                              <1> DirectColorModeInfo23:	db	0
  1465                              <1> PhysBasePtr23:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1466                              <1> OffScreenMemOffset23:	dd	0
  1467                              <1> OffScreenMemSize23:	dw	0
  1468                              <1> LinBytesPerScanLine23:	dw	5760
  1469                              <1> BnkNumberOfPages23: 	db	0
  1470                              <1> LinNumberOfPages23: 	db	0
  1471                              <1> LinRedMaskSize23:	db	8
  1472                              <1> LinRedFieldPosition23:	db	16
  1473                              <1> LinGreenMaskSize23:	db	8
  1474                              <1> LinGreenFieldPosition23:db	8
  1475                              <1> LinBlueMaskSize23:	db	8
  1476                              <1> LinBlueFieldPosition23:	db	0
  1477                              <1> LinRsvdMaskSize23:	db	0
  1478                              <1> LinRsvdFieldPosition23:	db	0
  1479                              <1> MaxPixelClock23:	dd	0
  1480                              <1> 
  1481                              <1> 			dw	0192h ; 1920x1080x32
  1482                              <1> ModeAttributes24: 	dw	MODE_ATTRIBUTES
  1483                              <1> WinAAttributes24: 	db	WINA_ATTRIBUTES
  1484                              <1> WinBAttributes24: 	db	0
  1485                              <1> WinGranularity24: 	dw	VBE_DISPI_BANK_SIZE_KB
  1486                              <1> WinSize24: 		dw	VBE_DISPI_BANK_SIZE_KB
  1487                              <1> WinASegment24:		dw	VGAMEM_GRAPH
  1488                              <1> WinBSegment24:		dw	0000h
  1489                              <1> WinFuncPtr24:		dd	0
  1490                              <1> BytesPerScanLine24:	dw	7680
  1491                              <1> XResolution24:		dw	1920
  1492                              <1> YResolution24:		dw	1080
  1493                              <1> XCharSize24:		db	8
  1494                              <1> YCharSize24:		db	16
  1495                              <1> NumberOfPlanes24:	db	1
  1496                              <1> BitsPerPixel24:		db	32
  1497                              <1> NumberOfBanks24:	db	127
  1498                              <1> MemoryModel24:		db	VBE_MEMORYMODEL_DIRECT_COLOR
  1499                              <1> BankSize24:		db	0
  1500                              <1> NumberOfImagePages24:	db	1
  1501                              <1> Reserved_page24:	db	0
  1502                              <1> RedMaskSize24:		db	8
  1503                              <1> RedFieldPosition24:	db	16
  1504                              <1> GreenMaskSize24:	db	8
  1505                              <1> GreenFieldPosition24:	db	8
  1506                              <1> BlueMaskSize24:		db	8
  1507                              <1> BlueFieldPosition24:	db	0
  1508                              <1> RsvdMaskSize24:		db	8
  1509                              <1> RsvdFieldPosition24:	db	24
  1510                              <1> DirectColorModeInfo24:	db	VBE_DIRECTCOLOR_RESERVED_BITS_AVAILABLE
  1511                              <1> PhysBasePtr24:		dd	VBE_DISPI_LFB_PHYSICAL_ADDRESS
  1512                              <1> OffScreenMemOffset24:	dd	0
  1513                              <1> OffScreenMemSize24:	dw	0
  1514                              <1> LinBytesPerScanLine24:	dw 	7680
  1515                              <1> BnkNumberOfPages24: 	db	0
  1516                              <1> LinNumberOfPages24: 	db	0
  1517                              <1> LinRedMaskSize24:	db	8
  1518                              <1> LinRedFieldPosition24:	db	16
  1519                              <1> LinGreenMaskSize24:	db	8
  1520                              <1> LinGreenFieldPosition24:db	8
  1521                              <1> LinBlueMaskSize24:	db	8
  1522                              <1> LinBlueFieldPosition24:	db	0
  1523                              <1> LinRsvdMaskSize24:	db	8
  1524                              <1> LinRsvdFieldPosition24:	db	24
  1525                              <1> MaxPixelClock24:	dd	0
  1526                              <1> 
  1527                              <1> VBE_VESA_MODE_END_OF_LIST: dw	0
  1528                              <1> 
  1529                              <1> %endif
  1530                              <1> 
  1531                              <1> ; 24/11/2020
  1532                              <1> 
  1533                              <1> direct_color_fields:
  1534                              <1> 	; 24/11/2020
  1535                              <1> 
  1536                              <1> ; (vbetables-gen.c)
  1537                              <1> ; // Direct Color fields 
  1538                              <1> ; (required for direct/6 and YUV/7 memory models)
  1539                              <1> ; switch(pm->depth) {
  1540                              <1>     
  1541                              <1> ;case 8:
  1542 00006AC6 00                  <1> r_size_8:  db 0
  1543 00006AC7 00                  <1> r_pos_8:   db 0
  1544 00006AC8 00                  <1> g_size_8:  db 0
  1545 00006AC9 00                  <1> g_pos_8:   db 0
  1546 00006ACA 00                  <1> b_size_8:  db 0
  1547 00006ACB 00                  <1> b_pos_8:   db 0
  1548 00006ACC 00                  <1> a_size_8:  db 0
  1549 00006ACD 00                  <1> a_pos_8:   db 0
  1550                              <1> 
  1551                              <1> ;case 16:
  1552 00006ACE 05                  <1> r_size_16:  db 5
  1553 00006ACF 0B                  <1> r_pos_16:   db 11
  1554 00006AD0 06                  <1> g_size_16:  db 6
  1555 00006AD1 05                  <1> g_pos_16:   db 5
  1556 00006AD2 05                  <1> b_size_16:  db 5
  1557 00006AD3 00                  <1> b_pos_16:   db 0
  1558 00006AD4 00                  <1> a_size_16:  db 0
  1559 00006AD5 00                  <1> a_pos_16:   db 0
  1560                              <1> 
  1561                              <1> ;case 24:
  1562 00006AD6 08                  <1> r_size_24:  db 8
  1563 00006AD7 10                  <1> r_pos_24:   db 16
  1564 00006AD8 08                  <1> g_size_24:  db 8
  1565 00006AD9 08                  <1> g_pos_24:   db 8
  1566 00006ADA 08                  <1> b_size_24:  db 8
  1567 00006ADB 00                  <1> b_pos_24:   db 0
  1568 00006ADC 00                  <1> a_size_24:  db 0
  1569 00006ADD 00                  <1> a_pos_24:   db 0
  1570                              <1> 
  1571                              <1> ;case 32:
  1572 00006ADE 08                  <1> r_size_32:  db 8
  1573 00006ADF 10                  <1> r_pos_32:   db 16
  1574 00006AE0 08                  <1> g_size_32:  db 8
  1575 00006AE1 08                  <1> g_pos_32:   db 8
  1576 00006AE2 08                  <1> b_size_32:  db 8
  1577 00006AE3 00                  <1> b_pos_32:   db 0
  1578 00006AE4 08                  <1> a_size_32:  db 8
  1579 00006AE5 18                  <1> a_pos_32:   db 24
  2854                                  ;%include 'diskdata.s'	; DISK (BIOS) DATA (initialized)
  2855                                  ;;;
  2856                                  
  2857                                  Align 2
  2858                                  
  2859                                  %include 'sysdefs.s' ; 24/01/2015
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - SYSTEM DEFINITIONS : sysdefs.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 31/12/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    11                              <1> ; sysdefs.inc (14/11/2015)
    12                              <1> ; ****************************************************************************
    13                              <1> 
    14                              <1> ; Retro UNIX 386 v1 Kernel - SYSDEFS.INC
    15                              <1> ; Last Modification: 14/11/2015
    16                              <1> ;
    17                              <1> ; ///////// RETRO UNIX 386 V1 SYSTEM DEFINITIONS ///////////////
    18                              <1> ; (Modified from 
    19                              <1> ;	Retro UNIX 8086 v1 system definitions in 'UNIX.ASM', 01/09/2014)
    20                              <1> ; ((UNIX.ASM (RETRO UNIX 8086 V1 Kernel), 11/03/2013 - 01/09/2014))
    21                              <1> ; 	UNIX.ASM (MASM 6.11) --> SYSDEFS.INC (NASM 2.11)
    22                              <1> ; ----------------------------------------------------------------------------
    23                              <1> ;
    24                              <1> ; Derived from UNIX Operating System (v1.0 for PDP-11) 
    25                              <1> ; (Original) Source Code by Ken Thompson (1971-1972)
    26                              <1> ; <Bell Laboratories (17/3/1972)>
    27                              <1> ; <Preliminary Release of UNIX Implementation Document>
    28                              <1> ;
    29                              <1> ; ****************************************************************************
    30                              <1> 
    31                              <1> nproc 	equ	16  ; number of processes
    32                              <1> nfiles 	equ	50
    33                              <1> ntty	equ     8   ; 8+1 -> 8 (10/05/2013)
    34                              <1> nbuf	equ	4   ; 6 ;; 21/08/2015 - 'namei' buffer problem when nbuf > 4 	
    35                              <1> 		; NOTE: If fd0 super block buffer addres is beyond of the 1st
    36                              <1> 		; 32K, DMA r/w routine or someting else causes a jump to 
    37                              <1> 		; kernel panic routine (in 'alloc' routine, in u5.s)
    38                              <1> 		; because of invalid buffer content (r/w error). 
    39                              <1> 		; When all buffers are set before the end of the 1st 32k,
    40                              <1> 		; there is no problem!? (14/11/2015) 
    41                              <1> 
    42                              <1> ;csgmnt	equ	2000h	; 26/05/2013 (segment of process 1)
    43                              <1> ;core	equ 	0  	    ; 19/04/2013	
    44                              <1> ;ecore	equ	32768 - 64  ; 04/06/2013 (24/05/2013)
    45                              <1> 	; (if total size of argument list and arguments is 128 bytes)
    46                              <1> 	; maximum executable file size = 32768-(64+40+128-6) = 32530 bytes
    47                              <1> 	; maximum stack size = 40 bytes (+6 bytes for 'IRET' at 32570)	
    48                              <1> 	; initial value of user's stack pointer = 32768-64-128-2 = 32574
    49                              <1> 	; 	(sp=32768-args_space-2 at the beginning of execution)
    50                              <1> 	; argument list offset = 32768-64-128 = 32576 (if it is 128 bytes)
    51                              <1> 	; 'u' structure offset (for the '/core' dump file) = 32704
    52                              <1> 	; '/core' dump file size = 32768 bytes
    53                              <1>  
    54                              <1> ; 08/03/2014 
    55                              <1> ;sdsegmnt equ	6C0h  ; 256*16 bytes (swap data segment size for 16 processes)		 	 
    56                              <1> ; 19/04/2013 Retro UNIX 8086 v1 feaure only !
    57                              <1> ;;sdsegmnt equ 	740h  ; swap data segment (for user structures and registers)
    58                              <1> 
    59                              <1> ; 30/08/2013
    60                              <1> time_count equ 4 ; 10 --> 4 01/02/2014
    61                              <1> 
    62                              <1> ; 05/02/2014
    63                              <1> ; process status
    64                              <1> ;SFREE 	equ 0
    65                              <1> ;SRUN	equ 1
    66                              <1> ;SWAIT	equ 2
    67                              <1> ;SZOMB	equ 3
    68                              <1> ;SSLEEP	equ 4 ; Retro UNIX 8086 V1 extension (for sleep and wakeup)
    69                              <1> 
    70                              <1> ; 09/03/2015
    71                              <1> userdata equ 80000h ; user structure data address for current user ; temporary
    72                              <1> swap_queue equ 90000h - 2000h ; swap queue address ; temporary
    73                              <1> swap_alloc_table equ 0D0000h  ;  swap allocation table address ; temporary
    74                              <1> 
    75                              <1> ; 17/09/2015
    76                              <1> ESPACE equ 48 ; [u.usp] (at 'sysent') - [u.sp] value for error return
    77                              <1> 
    78                              <1> ; 31/12/2017
    79                              <1> ; 19/02/2017
    80                              <1> ; 15/10/2016
    81                              <1> ; 20/05/2016
    82                              <1> ; 19/05/2016
    83                              <1> ; 18/05/2016
    84                              <1> ; 29/04/2016 
    85                              <1> ; TRDOS 386 (TRDOS v2.0) system calls - temporary List 
    86                              <1> ; 14/07/2013 - 21/09/2015 (Retro UNIX 8086 & 386 system calls) 
    87                              <1> _ver 	equ 0 ; Get TRDOS version (v2.0)
    88                              <1> _exit 	equ 1
    89                              <1> _fork 	equ 2
    90                              <1> _read 	equ 3
    91                              <1> _write	equ 4
    92                              <1> _open	equ 5
    93                              <1> _close 	equ 6
    94                              <1> _wait 	equ 7
    95                              <1> _creat 	equ 8
    96                              <1> _rename	equ 9  ; TRDOS 386, Rename File (31/12/2017)	
    97                              <1> _delete	equ 10 ; TRDOS 386, Delete File (29/12/2017)
    98                              <1> _exec	equ 11
    99                              <1> _chdir	equ 12
   100                              <1> _time 	equ 13 ; TRDOS 386, Get Sys Date&Time (30/12/2017)
   101                              <1> _mkdir 	equ 14
   102                              <1> _chmod	equ 15 ; TRDOS 386, Change Attributes (30/12/2017) 
   103                              <1> _rmdir	equ 16 ; TRDOS 386, Remove Directory (29/12/2017)
   104                              <1> _break	equ 17
   105                              <1> _drive	equ 18 ; TRDOS 386, Get/Set Current Drv (30/12/2017) 
   106                              <1> _seek	equ 19
   107                              <1> _tell 	equ 20
   108                              <1> _mem	equ 21 ; TRDOS 386, Get Total&Free Mem (31/12/2017)
   109                              <1> _prompt	equ 22 ; TRDOS 386, Change Cmd Prompt (31/12/2017)
   110                              <1> _path	equ 23 ; TRDOS 386, Get/Set Run Path (31/12/2017)
   111                              <1> _env	equ 24 ; TRDOS 386, Get/Set Env Vars (31/12/2017)
   112                              <1> _stime	equ 25 ; TRDOS 386, Set Sys Date&Time (30/12/2017)
   113                              <1> _quit	equ 26	
   114                              <1> _intr	equ 27
   115                              <1> _dir	equ 28 ; TRDOS 386, Get Curr Drive&Dir (30/12/2017) 
   116                              <1> _emt 	equ 29
   117                              <1> _ldrvt 	equ 30 ; TRDOS 386, Get Logical DOS DDT (30/12/2017)
   118                              <1> _video  equ 31 ; TRDOS 386 Video Functions (16/05/2016)
   119                              <1> _audio	equ 32 ; TRDOS 386 Video Functions (16/05/2016)
   120                              <1> _timer	equ 33 ; TRDOS 386 Timer Functions (18/05/2016)
   121                              <1> _sleep	equ 34 ; Retro UNIX 8086 v1 feature only !
   122                              <1> _msg	equ 35 ; Retro UNIX 386 v1 feature only !
   123                              <1> _geterr	equ 36 ; Retro UNIX 386 v1 feature only !
   124                              <1> _fpsave equ 37 ; TRDOS 386 FPU state option (28/02/2017)
   125                              <1> _pri 	equ 38 ; change priority - TRDOS 386 (20/05/2016)
   126                              <1> _rele	equ 39 ; TRDOS 386 (19/05/2016)
   127                              <1> _fff	equ 40 ; Find First File - TRDOS 386 (15/10/2016)
   128                              <1> _fnf	equ 41 ; Find Next File - TRDOS 386 (15/10/2016)
   129                              <1> _alloc	equ 42 ; Allocate memory - TRDOS 386 (19/02/2017)
   130                              <1> 	       ; TRDOS 386 (19/02/2017) DMA buff fuctions		
   131                              <1> _dalloc equ 43 ; Deallocate mem - TRDOS 386 (19/02/2017)
   132                              <1> _calbac equ 44 ; Set IRQ callback - TRDOS 386 (20/02/2017)  				
   133                              <1> _dma	equ 45 ; DMA service - TRDOS 386 (20/08/2017)  
   134                              <1> 
   135                              <1> %macro sys 1-4
   136                              <1>     ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)	
   137                              <1>     ; 03/09/2015	
   138                              <1>     ; 13/04/2015
   139                              <1>     ; Retro UNIX 386 v1 system call.		
   140                              <1>     %if %0 >= 2   
   141                              <1>         mov ebx, %2
   142                              <1>         %if %0 >= 3    
   143                              <1>             mov ecx, %3
   144                              <1>             %if %0 = 4
   145                              <1>                mov edx, %4   
   146                              <1>             %endif
   147                              <1>         %endif
   148                              <1>     %endif
   149                              <1>     mov eax, %1
   150                              <1>     ;int 30h
   151                              <1>     int 40h ; TRDOS 386 (TRDOS v2.0)		   
   152                              <1> %endmacro
   153                              <1> 
   154                              <1> ; TRDOS 386 system calls, interrupt number
   155                              <1> ; 25/12/2016
   156                              <1> SYSCALL_INT_NUM   equ '40' ; '40h'
   157                              <1> 
   158                              <1> ; 13/05/2015 - ERROR CODES
   159                              <1> ERR_FILE_NOT_OPEN  equ 10 ; 'file not open !' error
   160                              <1> ERR_FILE_ACCESS    equ 11 ; 'permission denied !' error
   161                              <1> ; 14/05/2015
   162                              <1> ERR_DIR_ACCESS     equ 11 ; 'permission denied !' error
   163                              <1> ERR_FILE_NOT_FOUND equ 12 ; 'file not found !' error
   164                              <1> ERR_TOO_MANY_FILES equ 13 ; 'too many open files !' error
   165                              <1> ERR_DIR_EXISTS     equ 14 ; 'directory already exists !' error 	
   166                              <1> ; 16/05/2015		
   167                              <1> ERR_DRV_NOT_RDY    equ 15 ; 'drive not ready !' error
   168                              <1> ; 18/05/2015
   169                              <1> ERR_DEV_NOT_RDY    equ 15 ; 'device not ready !' error
   170                              <1> ERR_DEV_ACCESS     equ 11 ; 'permission denied !' error 
   171                              <1> ERR_DEV_NOT_OPEN   equ 10 ; 'device not open !' error	
   172                              <1> ; 07/06/2015
   173                              <1> ERR_FILE_EOF	   equ 16 ; 'end of file !' error
   174                              <1> ERR_DEV_VOL_SIZE   equ 16 ; 'out of volume !' error
   175                              <1> ; 09/06/2015
   176                              <1> ERR_DRV_READ	   equ 17 ; 'disk read error !'
   177                              <1> ERR_DRV_WRITE	   equ 18 ; 'disk write error !'
   178                              <1> ; 16/06/2015
   179                              <1> ERR_NOT_DIR	   equ 19 ; 'not a (valid) directory !' error
   180                              <1> ERR_FILE_SIZE	   equ 20 ; 'file size error !'	
   181                              <1> ; 22/06/2015
   182                              <1> ERR_NOT_SUPERUSER  equ 11 ; 'permission denied !' error
   183                              <1> ERR_NOT_OWNER      equ 11 ; 'permission denied !' error
   184                              <1> ERR_NOT_FILE       equ 11 ; 'permission denied !' error	
   185                              <1> ; 23/06/2015
   186                              <1> ERR_FILE_EXISTS    equ 14 ; 'file already exists !' error
   187                              <1> ERR_DRV_NOT_SAME   equ 21 ; 'not same drive !' error
   188                              <1> ERR_DIR_NOT_FOUND  equ 12 ; 'directory not found !' error
   189                              <1> ERR_NOT_EXECUTABLE equ 22 ; 'not executable file !' error
   190                              <1> ; 27/06/2015
   191                              <1> ERR_INV_PARAMETER  equ 23 ; 'invalid parameter !' error
   192                              <1> ERR_INV_DEV_NAME   equ 24 ; 'invalid device name !' error
   193                              <1> ; 29/06/2015
   194                              <1> ERR_TIME_OUT	   equ 25 ; 'time out !' error			
   195                              <1> ERR_DEV_NOT_RESP   equ 25 ; 'device not responding !' error
   196                              <1> ; 10/10/2016
   197                              <1> ERR_INV_FILE_NAME  equ 26 ; 'invalid file name !' error
   198                              <1> ERR_INV_FLAGS	   equ 23 ; 'invalid flags !' error
   199                              <1> ; For code compatibility with previous version of TRDOS (2011)
   200                              <1> ; (Temporary error codes for current TRDOS 386 -2016- version) 
   201                              <1> ERR_NO_MORE_FILES  equ 12 ; 'no more files !' error
   202                              <1> ERR_PATH_NOT_FOUND equ  3 ; 'path not found !' error 
   203                              <1> 			  ; 'dir not found !' ; TRDOS 8086
   204                              <1> ERR_NOT_FOUND:	   equ  2 ; 'file not found !' ; TRDOS 8086
   205                              <1> ERR_DISK_SPACE	   equ 39 ; 'out of volume !' TRDOS 8086
   206                              <1> 			  ; 'insufficient disk space !' ; 27h
   207                              <1> ERR_DISK_WRITE	   equ 30 ; 'disk write protected !' ; 16/10/2016
   208                              <1> ERR_ACCESS_DENIED  equ  5 ; 'access denied !' ; TRDOS 8086 	
   209                              <1> ; 28/02/2017
   210                              <1> ERR_PERM_DENIED	   equ 11 ; 'permission denied !' error  	
   211                              <1> ; 18/05/2016
   212                              <1> ERR_MISC	   equ 27 ; miscellaneous/other errors
   213                              <1> ; 15/10/2016
   214                              <1> ; TRDOS 8086 -> TRDOS 386 (0Bh -> 28)
   215                              <1> ERR_INV_FORMAT	   equ 28 ; 'invalid format !' error
   216                              <1> ; TRDOS 8086 -> TRDOS 386 (0Dh -> 29)
   217                              <1> ERR_INV_DATA	   equ 29 ; 'invalid data !' error
   218                              <1> ; TRDOS 8086 -> TRDOS 386 (0Eh -> 20)
   219                              <1> ERR_ZERO_LENGTH	   equ 20  ; 'zero length !' error 	
   220                              <1> ; TRDOS 8086 -> TRDOS 386 (15h -> 17, 1Dh -> 18, 1Eh -> 17) 	
   221                              <1> ERR_DRV_NR_READ	   equ 17 ; 'drive not ready or read error !'
   222                              <1> ERR_DRV_NR_WRITE   equ 18 ; 'drive not ready or write error !'		
   223                              <1> ; 15/10/2016
   224                              <1> ERR_INV_PATH_NAME  equ 19 ; 'bad path name !' error
   225                              <1> ERR_BAD_CMD_ARG	   equ  1 ; 'bad command argument !' ; TRDOS 8086
   226                              <1> ERR_INV_FNUMBER	   equ  1 ; 'invalid function number !' ; TRDOS 8086
   227                              <1> ERR_BIG_FILE	   equ  8 ; 'big file & out of memory ! ; TRDOS 8086 	
   228                              <1> ERR_BIG_DATA	   equ  8 ; 'big data & out of memory ! ; TRDOS 8086
   229                              <1> ERR_CLUSTER	   equ 35 ; 'cluster not available !' ; TRDOS 8086
   230                              <1> ERR_OUT_OF_MEMORY  equ  4 ; 'out of memory !'
   231                              <1> 			  ; 'insufficient memory !'
   232                              <1> ERR_P_VIOLATION	   equ	6 ; 'protection violation !'
   233                              <1> ERR_PAGE_FAULT	   equ 224 ;'page fault !' ;0E0h						 
   234                              <1> ERR_SWP_DISK_READ  	   equ 40
   235                              <1> ERR_SWP_DISK_NOT_PRESENT   equ 41
   236                              <1> ERR_SWP_SECTOR_NOT_PRESENT equ 42
   237                              <1> ERR_SWP_NO_FREE_SPACE      equ 43
   238                              <1> ERR_SWP_DISK_WRITE         equ 44
   239                              <1> ERR_SWP_NO_PAGE_TO_SWAP    equ 45
   240                              <1> ; 10/04/2017
   241                              <1> ERR_BUFFER	   equ 46  ; 'buffer error !'
   242                              <1> ; 28/08/2017 (20/08/2017)
   243                              <1> ERR_DMA		   equ -1  ; DMA buffer (allocation/misc.) error!
   244                              <1> 
   245                              <1> ; 26/08/2015
   246                              <1> ; 24/07/2015
   247                              <1> ; 24/06/2015
   248                              <1> MAX_ARG_LEN	   equ 256 ; max. length of sys exec arguments
   249                              <1> ; 01/07/2015
   250                              <1> MAX_MSG_LEN	   equ 255 ; max. msg length for 'sysmsg'
   251                              <1> ;	
   252                              <1> ; 06/10/2016
   253                              <1> OPENFILES	   equ 10  ; max. number of open files (system)
   254                              <1> ; 07/10/2016
   255                              <1> ;NUMOFDEVICES	   equ 20  ; max. num of available devices (sys)
   256                              <1> 			 		
  2860                                  %include 'trdosk0.s' ; 04/01/2016 
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - DEFINITIONS : trdosk0.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 29/02/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 04/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; TRDOS2.ASM (09/11/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; TRDOS2.ASM (c) 2004-2011 Erdogan TAN [ 17/01/2004 ] Last Update: 09/11/2011
    14                              <1> ;
    15                              <1> ; Masterboot / Partition Table at Beginning+1BEh
    16                              <1> ptBootable       equ 0
    17                              <1> ptBeginHead      equ 1
    18                              <1> ptBeginSector    equ 2
    19                              <1> ptBeginCylinder  equ 3
    20                              <1> ptFileSystemID   equ 4
    21                              <1> ptEndHead        equ 5
    22                              <1> ptEndSector      equ 6
    23                              <1> ptEndCylinder    equ 7
    24                              <1> ptStartSector    equ 8
    25                              <1> ptSectors        equ 12
    26                              <1> 
    27                              <1> ; Boot Sector Parameters at 7C00h
    28                              <1> DataArea1     equ -4
    29                              <1> DataArea2     equ -2
    30                              <1> BootStart     equ 0h
    31                              <1> OemName       equ 03h
    32                              <1> BytesPerSec   equ 0Bh
    33                              <1> SecPerClust   equ 0Dh
    34                              <1> ResSectors    equ 0Eh
    35                              <1> FATs          equ 10h
    36                              <1> RootDirEnts   equ 11h
    37                              <1> Sectors       equ 13h
    38                              <1> Media         equ 15h
    39                              <1> FATSecs       equ 16h
    40                              <1> SecPerTrack   equ 18h
    41                              <1> Heads         equ 1Ah 
    42                              <1> Hidden1       equ 1Ch
    43                              <1> Hidden2       equ 1Eh
    44                              <1> HugeSec1      equ 20h
    45                              <1> HugeSec2      equ 22h
    46                              <1> DriveNumber   equ 24h
    47                              <1> Reserved1     equ 25h
    48                              <1> bootsignature equ 26h                 
    49                              <1> VolumeID      equ 27h
    50                              <1> VolumeLabel   equ 2Bh
    51                              <1> FileSysType   equ 36h          
    52                              <1> Reserved2     equ 3Eh                           ; Starting cluster of P2000
    53                              <1> 
    54                              <1> ; FAT32 BPB Structure
    55                              <1> FAT32_FAT_Size equ 36
    56                              <1> FAT32_RootFClust equ 44
    57                              <1> FAT32_FSInfoSec equ 48
    58                              <1> FAT32_DrvNum equ 64
    59                              <1> FAT32_BootSig equ 66
    60                              <1> FAT32_VolID equ 67
    61                              <1> FAT32_VolLab equ 71
    62                              <1> FAT32_FilSysType equ 82
    63                              <1> 
    64                              <1> ; BIOS Disk Parameters
    65                              <1> DPDiskNumber  equ 0h
    66                              <1> DPDType       equ 1h
    67                              <1> DPReturn      equ 2h
    68                              <1> DPHeads       equ 3h
    69                              <1> DPCylinders   equ 4h
    70                              <1> DPSecPerTrack equ 6h
    71                              <1> DPDisks       equ 7h
    72                              <1> DPTableOff    equ 8h
    73                              <1> DPTableSeg    equ 0Ah
    74                              <1> DPNumOfSecs   equ 0Ch
    75                              <1> 
    76                              <1> ; BIOS INT 13h Extensions (LBA extensions)
    77                              <1> ; Just After DP Data (DPDiskNumber+)
    78                              <1> DAP_PacketSize equ 10h  ; If extensions present, this byte will be >=10h
    79                              <1> DAP_Reserved1 equ 11h   ; Reserved Byte 
    80                              <1> DAP_NumOfBlocks equ 12h ; Value of this byte must be 0 to 127
    81                              <1> DAP_Reserved2 equ 13h   ; Reserved Byte
    82                              <1> DAP_Destination equ 14h ; Address of Transfer Buffer as SEGMENT:OFFSET
    83                              <1> DAP_LBA_Address equ 18h ; LBA=(C1*H0+H1)*S0+S1-1
    84                              <1>                         ; C1= Selected Cylinder Number
    85                              <1>                         ; H0= Number Of Heads (Maximum Head Number + 1)
    86                              <1>                         ; H1= Selected Head Number
    87                              <1>                         ; S0= Maximum Sector Number
    88                              <1>                         ; S1= Selected Sector Number
    89                              <1>                         ; QUAD WORD
    90                              <1> ; DAP_Flat_Destination equ 20h ; 64 bit address, if value in 4h is FFFF:FFFFh
    91                              <1>                              ; QUAD WORD (Also, value in 0h must be 18h) 
    92                              <1>                              ; TR-DOS will not use 64 bit Flat Address
    93                              <1> 
    94                              <1> ; INT 13h Function 48h "Get Enhanced Disk Drive Parameters"
    95                              <1> ; Just After DP Data (DPDiskNumber+)
    96                              <1> GetDParams_48h equ 20h ; Word. Data Length, must be 26 (1Ah) for short data.
    97                              <1> GDP_48h_InfoFlag equ 22h ; Word
    98                              <1> ; Bit 1 = 1 -> The geometry returned in bytes 4-15 is valid.
    99                              <1> GDP_48h_NumOfPCyls equ 24h ; Double Word. Number physical cylinders.
   100                              <1> GDP_48h_NumOfPHeads equ 28h ; Double Word. Number of physical heads.
   101                              <1> GDP_48h_NumOfPSpT equ 2Ch ; Double word. Num of physical sectors per track.
   102                              <1> GDP_48h_LBA_Sectors equ 30h ; 8 bytes. Number of physical/LBA sectors.
   103                              <1> GDP_48h_BytesPerSec equ 38h ; Word. Number of bytes in a sector.
   104                              <1> 
   105                              <1> ; TR-DOS Standalone Program Extensions to the DiskParams Block
   106                              <1> ; Just After DP Data (DPDiskNumber+)
   107                              <1> TRDP_CurrentSector equ 3Ah  ; DX:AX (LBA)
   108                              <1> TRDP_SectorCount equ 3Eh    ; CX (or Counter)
   109                              <1> 
   110                              <1> 
   111                              <1> ; DOS Logical Disks
   112                              <1> LD_Name equ 0
   113                              <1> LD_DiskType equ 1
   114                              <1> LD_PhyDrvNo equ 2
   115                              <1> LD_FATType equ 3
   116                              <1> LD_FSType equ 4
   117                              <1> LD_LBAYes equ 5
   118                              <1> LD_BPB equ 6
   119                              <1> LD_FATBegin equ 96
   120                              <1> LD_ROOTBegin equ 100
   121                              <1> LD_DATABegin equ 104
   122                              <1> LD_StartSector equ 108
   123                              <1> LD_TotalSectors equ 112
   124                              <1> LD_FreeSectors equ 116
   125                              <1> LD_Clusters equ 120
   126                              <1> LD_PartitionEntry equ 124
   127                              <1> LD_DParamEntry equ 125
   128                              <1> LD_MediaChanged equ 126
   129                              <1> LD_CDirLevel equ 127
   130                              <1> LD_CurrentDirectory equ 128
   131                              <1> 
   132                              <1> ; Singlix FS Extensions to DOS Logical Disks
   133                              <1> ; 03/01/2010 (LD_BPB compatibility for CHS r/w)
   134                              <1> 
   135                              <1> LD_FS_Name equ 0
   136                              <1> LD_FS_DiskType equ 1
   137                              <1> LD_FS_PhyDrvNo equ 2
   138                              <1> LD_FS_FATType equ 3
   139                              <1> LD_FS_FSType equ 4
   140                              <1> LD_FS_LBAYes equ 5
   141                              <1> LD_FS_BPB equ 6
   142                              <1> LD_FS_MediaAttrib equ 6
   143                              <1> LD_FS_VersionMajor equ 7
   144                              <1> LD_FS_RootDirD equ 8
   145                              <1> LD_FS_MATLocation equ 12
   146                              <1> LD_FS_Reserved1 equ 16 ;1 reserved byte
   147                              <1> LD_FS_BytesPerSec equ 17 ; LD_BPB + 0Bh
   148                              <1> LD_FS_Reserved2 equ 19 ;2 reserved byte
   149                              <1> LD_FS_DATLocation equ 20
   150                              <1> LD_FS_DATSectors equ 24
   151                              <1> LD_FS_Reserved3 equ 28 ;3 reserved word
   152                              <1> LD_FS_SecPerTrack equ 30 ; LD_BPB + 18h
   153                              <1> LD_FS_NumHeads equ 32    ; LD_BPB + 1Ah
   154                              <1> LD_FS_UnDelDirD equ 34
   155                              <1> LD_FS_Reserved4 equ 38 ;4 reserved word
   156                              <1> LD_FS_VolumeSerial equ 40
   157                              <1> LD_FS_VolumeName equ 44
   158                              <1> LD_FS_BeginSector equ 108
   159                              <1> LD_FS_VolumeSize equ 112
   160                              <1> LD_FS_FreeSectors equ 116
   161                              <1> LD_FS_FirstFreeSector equ 120
   162                              <1> LD_FS_PartitionEntry equ 124
   163                              <1> LD_FS_DParamEntry equ 125
   164                              <1> LD_FS_MediaChanged equ 126
   165                              <1> LD_FS_CDirLevel equ 127
   166                              <1> LD_FS_CDIR_Converted equ 128
   167                              <1> 
   168                              <1> ; Valid FAT Types
   169                              <1> FS_FAT12 equ 1
   170                              <1> FS_FAT16_CHS equ 2
   171                              <1> FS_FAT32_CHS equ 3
   172                              <1> FS_FAT16_LBA equ 4
   173                              <1> FS_FAT32_LBA equ 5
   174                              <1> 
   175                              <1> ; Cursor Location
   176                              <1> CCCpointer equ  0450h   ; BIOS data, current cursor column
   177                              <1> ; FAT Clusters EOC sign
   178                              <1> FAT12EOC equ 0FFFh
   179                              <1> FAT16EOC equ 0FFFFh
   180                              <1> ;FAT32EOC equ 0FFFFFFFh ; It is not direct usable for 8086 code
   181                              <1> ; BAD Cluster
   182                              <1> FAT12BADC equ 0FF7h
   183                              <1> FAT16BADC equ 0FFF7h
   184                              <1> ;FAT32BADC equ 0FFFFFF7h ; It is not direct usable for 8086 code
   185                              <1> ; MS-DOS FAT16 FS (Maximum Possible) Last Cluster Number= 0FFF6h 
   186                              <1> 
   187                              <1> ; TRFS
   188                              <1> 
   189                              <1> bs_FS_JmpBoot equ 0 ; jmp short bsBootCode
   190                              <1>                 ; db 0EBh, db 3Fh, db 90h
   191                              <1> bs_FS_Identifier equ 3  ; db 'FS', db 0
   192                              <1> bs_FS_BytesPerSec equ 6 ; dw 512
   193                              <1> bs_FS_MediaAttrib equ 8 ; db 3
   194                              <1> bs_FS_PartitionID equ 9 ; db 0A1h
   195                              <1> bs_FS_VersionMaj equ 10 ; db 01h
   196                              <1> bs_FS_VersionMin equ 11 ; db 0
   197                              <1> bs_FS_BeginSector equ 12   ; dd 0 
   198                              <1> bs_FS_VolumeSize equ 16 ; dd 2880
   199                              <1> bs_FS_StartupFD equ 20 ; dd 0
   200                              <1> bs_FS_MATLocation equ 24 ; dd 1
   201                              <1> bs_FS_RootDirD equ 28 ; dd 8
   202                              <1> bs_FS_SystemConfFD equ 32 ; dd 0
   203                              <1> bs_FS_SwapFD equ 36 ; dd 0
   204                              <1> bs_FS_UnDelDirD equ 40 ; dd 0
   205                              <1> bs_FS_DriveNumber equ 44 ; db 0
   206                              <1> bs_FS_LBA_Ready equ 45 ; db 0
   207                              <1> bs_FS_MagicWord equ 46 
   208                              <1> bs_FS_SecPerTrack equ 46 ; db 0A1h
   209                              <1> bs_FS_Heads equ 47 ; db 01h 
   210                              <1> bs_FS_OperationSys equ 48 ; db "TR-SINGLIX v1.0b"
   211                              <1> bs_FS_Terminator equ 64 ; db 0
   212                              <1> bs_FS_BootCode equ 65 
   213                              <1> 
   214                              <1> FS_MAT_DATLocation equ 12
   215                              <1> FS_MAT_DATScount equ 16
   216                              <1> FS_MAT_FreeSectors equ 20
   217                              <1> FS_MAT_FirstFreeSector equ 24
   218                              <1> FS_RDT_VolumeSerialNo equ 28
   219                              <1> FS_RDT_VolumeName equ 64
   220                              <1> 
   221                              <1> ; FAT12 + FAT16 + FAT32
   222                              <1> BS_JmpBoot equ 0
   223                              <1> BS_OEMName equ 3
   224                              <1> BPB_BytsPerSec equ 11
   225                              <1> BPB_SecPerClust equ 13
   226                              <1> BPB_RsvdSecCnt equ 14
   227                              <1> BPB_NumFATs equ 16
   228                              <1> BPB_RootEntCnt equ 17
   229                              <1> BPB_TotalSec16 equ 19
   230                              <1> BPB_Media equ 21
   231                              <1> BPB_FATSz16 equ 22
   232                              <1> BPB_SecPerTrk equ 24
   233                              <1> BPB_NumHeads equ 26
   234                              <1> BPB_HiddSec equ 28
   235                              <1> BPB_TotalSec32 equ 32
   236                              <1> 
   237                              <1> ; FAT12 and FAT16 only
   238                              <1> BS_DrvNum equ 36
   239                              <1> BS_Reserved1 equ 37
   240                              <1> BS_BootSig equ 38
   241                              <1> BS_VolID equ 39
   242                              <1> BS_VolLab equ 43
   243                              <1> BS_FilSysType equ 54 ; 8 bytes
   244                              <1> BS_BootCode equ 62
   245                              <1> 
   246                              <1> ; FAT32 only
   247                              <1> BPB_FATSz32 equ 36 ; FAT32, 4 bytes
   248                              <1> BPB_ExtFlags equ 40 ; FAT32, 2 bytes
   249                              <1> BPB_FSVer equ 42 ; FAT32, 2 bytes
   250                              <1> BPB_RootClus equ 44 ; FAT32, 4 bytes
   251                              <1> BPB_FSInfo equ 48 ; FAT 32, 2 bytes 
   252                              <1> BPB_BkBootSec equ 50 ; FAT32, 2 bytes
   253                              <1> BPB_Reserved equ 52 ; FAT32, 12 bytes
   254                              <1> BS_FAT32_DrvNum equ 64 ; FAT32, 1 byte
   255                              <1> BS_FAT32_Reserved1 equ 65 ; FAT32, 1 byte
   256                              <1> BS_FAT32_BootSig equ 66 ; FAT32, 1 byte
   257                              <1> BS_FAT32_VolID equ 67 ; FAT32, 4 bytes
   258                              <1> BS_FAT32_VolLab equ 71 ; FAT32, 11 bytes
   259                              <1> BS_FAT32_FilSysType equ 82 ; FAT32, 8 bytes
   260                              <1> BS_FAT32_BootCode equ 90
   261                              <1> 
   262                              <1> ; 29/02/2016
   263                              <1> ;(FAT32 Free Cluster Count & First Free Cluster values)
   264                              <1> ;[BPB_Reserved] = Free Cluster Count (offset 52)
   265                              <1> ;[BPB_Reserved+4] = First Free Cluster (offset 56)
   266                              <1> 
   267                              <1> BS_Validation equ 510
   268                              <1> 
   269                              <1> ; 15/02/2016
   270                              <1> ; FILE.ASM - 09/10/2011
   271                              <1> ; Directory Entry Structure
   272                              <1> ; 29/10/2009 (According to Microsoft FAT32 File System Specification)
   273                              <1> DirEntry_Name equ 0
   274                              <1> DirEntry_Attr equ 11
   275                              <1> DirEntry_NTRes equ 12
   276                              <1> DirEntry_CrtTimeTenth equ 13
   277                              <1> DirEntry_CrtTime equ 14
   278                              <1> DirEntry_CrtDate equ 16
   279                              <1> DirEntry_LastAccDate equ 18
   280                              <1> DirEntry_FstClusHI equ 20
   281                              <1> DirEntry_WrtTime equ 22
   282                              <1> DirEntry_WrtDate equ 24
   283                              <1> DirEntry_FstClusLO equ 26
   284                              <1> DirEntry_FileSize equ 28
  2861                                  %include 'trdosk1.s' ; 04/01/2016 
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.1) - SYS INIT : trdosk1.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 20/01/2018
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 04/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; TRDOS2.ASM (09/11/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; TRDOS2.ASM (c) 2004-2011 Erdogan TAN [ 17/01/2004 ] Last Update: 09/11/2011
    14                              <1> ;
    15                              <1> 
    16                              <1> sys_init:
    17                              <1> 	; 20/01/2018  (v2.0.1)
    18                              <1> 	; 23/01/2017  (v2.0.0)
    19                              <1> 	; 07/05/2016
    20                              <1> 	; 02/05/2016
    21                              <1> 	; 24/04/2016
    22                              <1> 	; 14/04/2016
    23                              <1> 	; 13/04/2016
    24                              <1> 	; 30/03/2016
    25                              <1> 	; 24/01/2016
    26                              <1> 	; 06/01/2016
    27                              <1> 	; 04/01/2016
    28                              <1> 
    29                              <1> 	; 23/01/2017 - reset timer frequency (to 18.2Hz)
    30 00006AE6 B036                <1> 	mov	al, 00110110b ; 36h
    31 00006AE8 E643                <1>  	out	43h, al
    32 00006AEA 31C0                <1> 	xor	eax, eax  ; sub	al, al ; 0
    33 00006AEC E640                <1> 	out	40h, al ; LB
    34 00006AEE E640                <1> 	out	40h, al ; HB
    35                              <1>  	; 
    36                              <1> 	; 30/03/2016
    37                              <1> 	; Clear Logical DOS Disk Description Tables Area
    38                              <1> 	;xor	eax, eax
    39 00006AF0 BF00010900          <1> 	mov	edi, Logical_DOSDisks
    40 00006AF5 B980060000          <1> 	mov	ecx, 6656/4 ; 26*256 = 6656 bytes
    41 00006AFA F3AB                <1> 	rep	stosd ; 1664 times 4 bytes
    42                              <1> 
    43 00006AFC B83F3A2F00          <1> 	mov	eax, '?:/'
    44 00006B01 A3[475F0100]        <1> 	mov	[Current_Dir_Drv], eax
    45                              <1> 
    46                              <1> 	; Logical DRV INIT (only for hard disks)
    47 00006B06 E813040000          <1> 	call 	ldrv_init  ; trdosk2.s
    48                              <1> 	
    49                              <1> 	; When floppy_drv_init call is disabled
    50                              <1> 	; media changed sign is needed
    51                              <1> 	; for proper drive initialization
    52                              <1>         
    53 00006B0B BE00010900          <1> 	mov 	esi, Logical_DOSDisks
    54 00006B10 B001                <1> 	mov 	al, 1 ; Initialization sign (invalid_fd_parameter)
    55 00006B12 83C67E              <1> 	add 	esi, LD_MediaChanged ; Media Change Status = 1 (init needed)
    56 00006B15 8806                <1> 	mov 	[esi], al ; A:
    57 00006B17 81C600010000        <1> 	add 	esi, 100h 
    58 00006B1D 8806                <1> 	mov 	[esi], al ; B: 
    59                              <1>            
    60                              <1> _current_drive_bootdisk:
    61 00006B1F 8A15[AA640000]      <1> 	mov 	dl, [boot_drv] ; physical drive number
    62 00006B25 80FAFF              <1> 	cmp 	dl, 0FFh
    63 00006B28 740A                <1> 	je 	short _last_dos_diskno_check
    64                              <1> _boot_drive_check:
    65 00006B2A 80FA80              <1> 	cmp 	dl, 80h
    66 00006B2D 7218                <1> 	jb 	short _current_drive_a
    67 00006B2F 80EA7E              <1> 	sub 	dl, 7Eh ; C = 2 , D = 3
    68 00006B32 EB13                <1> 	jmp 	short _current_drive_a 
    69                              <1> 
    70                              <1> _last_dos_diskno_check:
    71 00006B34 8A15[C6120100]      <1> 	mov 	dl, [Last_DOS_DiskNo]
    72 00006B3A 80FA02              <1> 	cmp 	dl, 2
    73 00006B3D 7706                <1> 	ja 	short _current_drive_c
    74 00006B3F 7406                <1> 	je 	short _current_drive_a
    75 00006B41 30D2                <1> 	xor 	dl, dl ; A:
    76 00006B43 EB02                <1> 	jmp 	short _current_drive_a
    77                              <1> 
    78                              <1> _current_drive_c:
    79 00006B45 B202                <1> 	mov 	dl, 2 ; C:
    80                              <1> 
    81                              <1> _current_drive_a:
    82 00006B47 8815[AB640000]      <1> 	mov	[drv], dl
    83 00006B4D BE[C8120100]        <1>         mov     esi, msg_CRLF_temp
    84 00006B52 E8AE000000          <1> 	call 	print_msg
    85                              <1> 
    86 00006B57 8A15[AB640000]      <1> 	mov	dl, [drv]
    87                              <1> _default_drive_c:
    88 00006B5D E81A0C0000          <1> 	call 	change_current_drive
    89 00006B62 731C                <1> 	jnc 	short _start_mainprog
    90                              <1> 
    91                              <1> _drv_not_ready_error: 
    92 00006B64 BE[83150100]        <1> 	mov 	esi, msgl_drv_not_ready
    93 00006B69 E897000000          <1> 	call 	print_msg
    94                              <1>         ;jmp	_end_of_mainprog
    95                              <1> 
    96                              <1> 	; 20/01/2018
    97 00006B6E B202                <1> 	mov	dl, 2
    98 00006B70 3815[AB640000]      <1> 	cmp	[drv], dl
    99 00006B76 736B                <1> 	jnb	short _end_of_mainprog
   100 00006B78 8815[AB640000]      <1> 	mov	[drv], dl
   101 00006B7E EBDD                <1> 	jmp	short _default_drive_c
   102                              <1> 
   103                              <1> _start_mainprog:
   104                              <1> 	; 07/01/2017
   105                              <1> 	; 07/05/2016
   106                              <1> 	; 02/05/2016
   107                              <1> 	; 24/04/2016
   108                              <1> 	; Retro UNIX 386 v1, 'sys_init' (u0.s)
   109                              <1> 	; 23/06/2015
   110                              <1> 
   111                              <1> 	; 02/05/2016
   112                              <1> 	; 24/04/2016
   113 00006B80 66B80100            <1> 	mov	ax, 1
   114 00006B84 A2[B3030300]        <1> 	mov	[u.uno], al
   115 00006B89 66A3[4E030300]      <1> 	mov	[mpid], ax
   116 00006B8F 66A3[20000300]      <1> 	mov	[p.pid], ax
   117 00006B95 A2[B0000300]        <1> 	mov	[p.stat], al
   118 00006B9A C605[A8030300]04    <1> 	mov	byte [u.quant], time_count  ; 07/01/2017
   119                              <1> 	;
   120 00006BA1 A1[805E0100]        <1> 	mov	eax, [k_page_dir]
   121 00006BA6 A3[B8030300]        <1> 	mov	[u.pgdir], eax ; reset
   122                              <1> 	;
   123 00006BAB E835E7FFFF          <1> 	call	allocate_page
   124 00006BB0 0F82A3000000        <1> 	jc	panic
   125 00006BB6 A3[B4030300]        <1> 	mov	[u.upage], eax ; user structure page	
   126 00006BBB A3[C0000300]        <1> 	mov	[p.upage], eax
   127 00006BC0 E89AE7FFFF          <1> 	call	clear_page
   128                              <1> 	;
   129                              <1> 	; 24/08/2015
   130 00006BC5 FE0D[5B030300]      <1> 	dec 	byte [sysflg] ; FFh = ready for system call
   131                              <1> 			      ; 0 = executing a system call
   132                              <1> 	; 13/04/2016
   133                              <1> 	; Clear Environment Variables Page/Area
   134 00006BCB BF00300900          <1> 	mov	edi, Env_Page ; 93000h
   135 00006BD0 B980000000          <1> 	mov	ecx, Env_Page_Size / 4 	; 512/4  (4096/4)				 	  		 	  
   136 00006BD5 31C0                <1> 	xor	eax, eax
   137 00006BD7 F3AB                <1> 	rep	stosd
   138                              <1> 
   139                              <1> 	; 14/04/2016
   140 00006BD9 E8F5340000          <1>  	call	mainprog_startup_configuration
   141                              <1> 
   142 00006BDE E8DA0C0000          <1>         call    dos_prompt
   143                              <1>               
   144                              <1> _end_of_mainprog:
   145 00006BE3 BE[C8120100]        <1>         mov     esi, msg_CRLF_temp
   146 00006BE8 E818000000          <1> 	call 	print_msg
   147 00006BED BE[CE120100]        <1> 	mov 	esi, mainprog_Version
   148 00006BF2 E80E000000          <1> 	call 	print_msg
   149                              <1> 	; 24/01/2016
   150 00006BF7 28E4                <1> 	sub	ah, ah
   151 00006BF9 E85CA2FFFF          <1> 	call	int16h ; call getch
   152 00006BFE E93CA7FFFF          <1> 	jmp	cpu_reset
   153                              <1> 
   154 00006C03 EBFE                <1> infinitiveloop: jmp short infinitiveloop
   155                              <1> 
   156                              <1> print_msg:
   157                              <1> 	; 13/05/2016
   158                              <1> 	; 04/01/2016
   159                              <1> 	; 01/07/2015
   160                              <1> 	; 13/03/2015 (Retro UNIX 386 v1)
   161                              <1> 	; 07/03/2014 (Retro UNIX 8086 v1)
   162                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX, ESI, EDI)
   163                              <1> 	;
   164 00006C05 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE] ; 04/01/2016 (ptty)
   165                              <1> 	;mov	bl, 07h ; Black background, light gray forecolor
   166                              <1> 
   167 00006C0B AC                  <1> 	lodsb
   168                              <1> pmsg1:
   169 00006C0C 56                  <1> 	push 	esi
   170                              <1> 	;mov	bh, [ACTIVE_PAGE] ; 04/01/2016 (ptty)
   171 00006C0D B307                <1> 	mov	bl, 07h ; Black background, light gray forecolor
   172 00006C0F E8C1B4FFFF          <1> 	call 	_write_tty
   173 00006C14 5E                  <1> 	pop	esi
   174 00006C15 AC                  <1> 	lodsb
   175 00006C16 20C0                <1> 	and 	al, al
   176 00006C18 75F2                <1> 	jnz 	short pmsg1
   177 00006C1A C3                  <1> 	retn
   178                              <1> 
   179                              <1> clear_screen:
   180                              <1> 	; 13/05/2016
   181                              <1> 	; 30/01/2016
   182                              <1> 	; 24/01/2016
   183                              <1> 	; 04/01/2016
   184 00006C1B 0FB61D[AE5E0100]    <1> 	movzx	ebx, byte [ACTIVE_PAGE] ; video page number (0 to 7)
   185 00006C22 8AA3[8B660000]      <1> 	mov 	ah, [ebx+vmode] ; default = 03h (80x25 text)
   186 00006C28 80FC04              <1> 	cmp	ah, 4
   187 00006C2B 7205                <1> 	jb	short cls1
   188 00006C2D 80FC07              <1> 	cmp	ah, 7
   189 00006C30 7526                <1> 	jne	short vga_clear
   190                              <1> cls1:
   191                              <1> 	;mov	bh, bl
   192                              <1> 	;mov	bl, 7
   193 00006C32 3A25[7A660000]      <1> 	cmp	ah, [CRT_MODE] ; current video mode ? 
   194                              <1> 	;je	short cls2 ; yes (current video mode = 3)
   195                              <1> 	;;call	set_mode_3 ; set video mode to 3 (& clear screen)
   196                              <1> 	;;retn
   197                              <1> 	;jmp	set_mode_3
   198 00006C38 0F85A1B4FFFF        <1> 	jne	set_mode_3
   199                              <1> cls2:
   200 00006C3E 88DF                <1> 	mov	bh, bl ; video page (0 to 7)
   201 00006C40 B307                <1> 	mov	bl, 07h ; attribute to be used on blanked line
   202 00006C42 28C0                <1> 	sub 	al, al ; 0 =  entire window
   203 00006C44 6631C9              <1> 	xor 	cx, cx
   204 00006C47 66BA4F18            <1> 	mov 	dx, 184Fh
   205 00006C4B E8BCB1FFFF          <1> 	call	_scroll_up ; 24/01/2016
   206                              <1> 	;
   207                              <1> 	;mov	bh, [ACTIVE_PAGE] ; video page number (0 to 7)
   208 00006C50 6631D2              <1> 	xor 	dx, dx
   209 00006C53 E81BB5FFFF          <1> 	call	_set_cpos ; 24/01/2016 
   210                              <1> 	;retn
   211                              <1> vga_clear:
   212 00006C58 C3                  <1> 	retn	
   213                              <1> 
   214                              <1> panic:
   215                              <1> 	; 13/05/2016 (TRDOS 386 = TRDOS v2)
   216                              <1> 	; 13/03/2015 (Retro UNIX 386 v1)
   217                              <1> 	; 07/03/2014 (Retro UNIX 8086 v1)
   218 00006C59 BE[661F0100]        <1> 	mov 	esi, panic_msg
   219 00006C5E E8A2FFFFFF          <1> 	call 	print_msg
   220                              <1> key_to_reboot:
   221                              <1>         ; 24/01/2016
   222 00006C63 28E4                <1>         sub     ah, ah
   223 00006C65 E8F0A1FFFF          <1>         call    int16h ; call   getch
   224                              <1>         ; wait for a character from the current tty
   225                              <1> 	;
   226 00006C6A B00A                <1> 	mov	al, 0Ah
   227 00006C6C 8A3D[AE5E0100]      <1> 	mov	bh, [ptty] ; [ACTIVE_PAGE]
   228 00006C72 B307                <1> 	mov	bl, 07h ; Black background, 
   229                              <1> 			; light gray forecolor
   230 00006C74 E85CB4FFFF          <1> 	call 	_write_tty
   231 00006C79 E9C1A6FFFF          <1> 	jmp	cpu_reset 
   232                              <1> 
   233                              <1> ctrlbrk:
   234                              <1> 	; 12/11/2015
   235                              <1> 	; 13/03/2015 (Retro UNIX 386 v1)
   236                              <1> 	; 06/12/2013 (Retro UNIX 8086 v1)
   237                              <1> 	;
   238                              <1> 	; INT 1Bh (control+break) handler		
   239                              <1> 	;
   240                              <1>       	; Retro Unix 8086 v1 feature only!
   241                              <1>       	;
   242 00006C7E 66833D[AA030300]00  <1> 	cmp 	word [u.intr], 0
   243 00006C86 7645                <1> 	jna 	short cbrk4
   244                              <1> cbrk0:
   245                              <1> 	; 12/11/2015
   246                              <1> 	; 06/12/2013
   247 00006C88 66833D[AC030300]00  <1> 	cmp 	word [u.quit], 0
   248 00006C90 743B                <1> 	jz	short cbrk4
   249                              <1> 	;
   250                              <1> 	; 20/09/2013	
   251 00006C92 6650                <1> 	push 	ax
   252 00006C94 A0[AE5E0100]        <1> 	mov	al, [ptty]
   253                              <1> 	;
   254                              <1> 	; 12/11/2015
   255                              <1> 	;
   256                              <1> 	; ctrl+break (EOT, CTRL+D) from serial port
   257                              <1> 	; or ctrl+break from console (pseudo) tty
   258                              <1> 	; (!redirection!)
   259                              <1> 	;
   260 00006C99 3C08                <1> 	cmp	al, 8 ; serial port tty nums > 7
   261 00006C9B 7211                <1>         jb      short cbrk1 ; console (pseudo) tty
   262                              <1> 	;	
   263                              <1> 	; Serial port interrupt handler sets [ptty]
   264                              <1> 	; to the port's tty number (as temporary).
   265                              <1> 	;
   266                              <1> 	; If active process is using a stdin or 
   267                              <1> 	; stdout redirection (by the shell),
   268                              <1>         ; console tty keyboard must be available
   269                              <1> 	; to terminate running process,
   270                              <1> 	; in order to prevent a deadlock. 
   271                              <1> 	;
   272 00006C9D 52                  <1> 	push	edx
   273 00006C9E 0FB615[B3030300]    <1> 	movzx	edx, byte [u.uno]
   274 00006CA5 3A82[7F000300]      <1> 	cmp     al, [edx+p.ttyc-1] ; console tty (rw)
   275 00006CAB 5A                  <1> 	pop	edx
   276 00006CAC 7412                <1> 	je	short cbrk2
   277                              <1> cbrk1:
   278 00006CAE FEC0                <1> 	inc 	al  ; [u.ttyp] : 1 based tty number
   279                              <1> 	; 06/12/2013
   280 00006CB0 3A05[94030300]      <1> 	cmp	al, [u.ttyp] ; recent open tty (r)
   281 00006CB6 7408                <1> 	je	short cbrk2	
   282 00006CB8 3A05[95030300]      <1>         cmp     al, [u.ttyp+1] ; recent open tty (w)
   283 00006CBE 750B                <1> 	jne	short cbrk3	
   284                              <1> cbrk2:
   285                              <1> 	;; 06/12/2013
   286                              <1> 	;mov	ax, [u.quit]
   287                              <1> 	;and	ax, ax
   288                              <1> 	;jz	short cbrk3
   289                              <1> 	;
   290 00006CC0 6631C0              <1> 	xor	ax, ax ; 0
   291 00006CC3 6648                <1> 	dec	ax
   292                              <1> 	; 0FFFFh = 'ctrl+brk' keystroke
   293 00006CC5 66A3[AC030300]      <1> 	mov	[u.quit], ax
   294                              <1> cbrk3:
   295 00006CCB 6658                <1> 	pop	ax
   296                              <1> cbrk4:
   297 00006CCD C3                  <1> 	retn
   298                              <1> 
   299                              <1> 
   300                              <1> ; 31/12/2017
   301                              <1> ; TRDOS 386 - 30/12/2017
   302                              <1> %define get_rtc_date RTC_40
   303                              <1> %define get_rtc_time RTC_20
   304                              <1> %define	set_rtc_date RTC_50
   305                              <1> %define set_rtc_time RTC_30	
   306                              <1> get_rtc_date_time:
   307                              <1> ; Retro UNIX 8086 v1 - UNIX.ASM (01/09/2014)
   308                              <1> ;epoch:
   309                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0)
   310                              <1> 	; 15/03/2015 (Retro UNIX 386 v1 - 32 bit version)
   311                              <1> 	; 09/04/2013 (Retro UNIX 8086 v1 - UNIX.ASM)
   312                              <1> 	; 'epoch' procedure prototype: 
   313                              <1> 	; 	            UNIXCOPY.ASM, 10/03/2013
   314                              <1> 	; 14/11/2012
   315                              <1> 	; unixboot.asm (boot file configuration)
   316                              <1> 	; version of "epoch" procedure in "unixproc.asm"
   317                              <1> 	; 21/7/2012
   318                              <1> 	; 15/7/2012
   319                              <1> 	; 14/7/2012		
   320                              <1> 	; Erdogan Tan - RETRO UNIX v0.1
   321                              <1> 	; compute current date and time as UNIX Epoch/Time
   322                              <1> 	; UNIX Epoch: seconds since 1/1/1970 00:00:00
   323                              <1> 	;
   324                              <1>         ;  ((Modified registers: EAX, EDX, ECX, EBX))  
   325                              <1> 	;
   326                              <1> 
   327 00006CCE E886F4FFFF          <1> 	call 	get_rtc_time		; Return Current Time
   328 00006CD3 86E9                <1>         xchg 	ch,cl
   329 00006CD5 66890D[4A5B0100]    <1>         mov 	[hour], cx
   330 00006CDC 86F2                <1>         xchg 	dh,dl
   331 00006CDE 668915[4E5B0100]    <1>         mov 	[second], dx
   332                              <1> 	;
   333 00006CE5 E8E0F4FFFF          <1>         call 	get_rtc_date		; Return Current Date
   334 00006CEA 86E9                <1>         xchg 	ch,cl
   335 00006CEC 66890D[445B0100]    <1>         mov 	[year], cx
   336 00006CF3 86F2                <1>         xchg 	dh,dl
   337 00006CF5 668915[465B0100]    <1>         mov 	[month], dx
   338                              <1> 	;
   339 00006CFC 66B93030            <1> 	mov 	cx, 3030h
   340                              <1> 	;
   341 00006D00 A0[4A5B0100]        <1> 	mov 	al, [hour] ; Hour
   342                              <1>         	; AL <= BCD number)
   343 00006D05 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   344                              <1> 					; AH = AL / 10h
   345                              <1> 					; AL = AL MOD 10h
   346 00006D07 D50A                <1>         aad 	; AX= AH*10+AL
   347 00006D09 A2[4A5B0100]        <1> 	mov 	[hour], al
   348 00006D0E A0[4B5B0100]        <1> 	mov 	al, [hour+1] ; Minute
   349                              <1>         	; AL <= BCD number)
   350 00006D13 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   351                              <1> 					; AH = AL / 10h
   352                              <1> 					; AL = AL MOD 10h
   353 00006D15 D50A                <1>         aad 	; AX= AH*10+AL
   354 00006D17 A2[4C5B0100]        <1> 	mov 	[minute], al
   355 00006D1C A0[4E5B0100]        <1> 	mov 	al, [second] ; Second
   356                              <1>         	; AL <= BCD number)
   357 00006D21 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   358                              <1> 					; AH = AL / 10h
   359                              <1> 					; AL = AL MOD 10h
   360 00006D23 D50A                <1>         aad 	; AX= AH*10+AL
   361 00006D25 A2[4E5B0100]        <1> 	mov 	[second], al
   362 00006D2A 66A1[445B0100]      <1> 	mov 	ax, [year] ; Year (century)
   363 00006D30 6650                <1>         push 	ax
   364                              <1> 	   	; AL <= BCD number)
   365 00006D32 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   366                              <1> 					; AH = AL / 10h
   367                              <1> 					; AL = AL MOD 10h
   368 00006D34 D50A                <1>         aad 	; AX= AH*10+AL
   369 00006D36 B464                <1> 	mov 	ah, 100
   370 00006D38 F6E4                <1> 	mul 	ah
   371 00006D3A 66A3[445B0100]      <1> 	mov 	[year], ax
   372 00006D40 6658                <1> 	pop	ax
   373 00006D42 88E0                <1> 	mov	al, ah
   374                              <1>         	; AL <= BCD number)
   375 00006D44 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   376                              <1> 					; AH = AL / 10h
   377                              <1> 					; AL = AL MOD 10h
   378 00006D46 D50A                <1>         aad 	; AX= AH*10+AL
   379 00006D48 660105[445B0100]    <1> 	add 	[year], ax
   380 00006D4F A0[465B0100]        <1> 	mov 	al, [month] ; Month
   381                              <1>            	; AL <= BCD number)
   382 00006D54 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   383                              <1> 					; AH = AL / 10h
   384                              <1> 					; AL = AL MOD 10h
   385 00006D56 D50A                <1>         aad 	; AX= AH*10+AL
   386 00006D58 A2[465B0100]        <1> 	mov 	[month], al	
   387 00006D5D A0[475B0100]        <1>         mov     al, [month+1]      	; Day
   388                              <1>            	; AL <= BCD number)
   389 00006D62 D410                <1>         db 	0D4h,10h		; Undocumented inst. AAM
   390                              <1> 					; AH = AL / 10h
   391                              <1> 					; AL = AL MOD 10h
   392 00006D64 D50A                <1>         aad 	; AX= AH*10+AL
   393 00006D66 A2[485B0100]        <1>         mov     [day], al
   394                              <1> 	
   395 00006D6B C3                  <1> 	retn	; 30/12/2017
   396                              <1> 
   397                              <1> epoch:
   398 00006D6C E85DFFFFFF          <1> 	call	get_rtc_date_time ; TRDOS 386 - 30/12/2017
   399                              <1> 
   400                              <1> convert_to_epoch:
   401                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0)
   402                              <1> 	; 15/03/2015 (Retro UNIX 386 v1 - 32 bit modification)
   403                              <1> 	; 09/04/2013 (Retro UNIX 8086 v1)
   404                              <1> 	;
   405                              <1> 	; ((Modified registers: EAX, EDX, EBX)) 
   406                              <1> 	;
   407                              <1> 	; Derived from DALLAS Semiconductor
   408                              <1> 	; Application Note 31 (DS1602/DS1603)
   409                              <1> 	; 6 May 1998
   410 00006D71 29C0                <1> 	sub 	eax, eax
   411 00006D73 66A1[445B0100]      <1> 	mov 	ax, [year]
   412 00006D79 662DB207            <1> 	sub 	ax, 1970
   413 00006D7D BA6D010000          <1> 	mov 	edx, 365
   414 00006D82 F7E2                <1> 	mul 	edx
   415 00006D84 31DB                <1> 	xor 	ebx, ebx
   416 00006D86 8A1D[465B0100]      <1> 	mov 	bl, [month]
   417 00006D8C FECB                <1> 	dec 	bl
   418 00006D8E D0E3                <1> 	shl 	bl, 1
   419                              <1> 	;sub	edx, edx
   420 00006D90 668B93[505B0100]    <1> 	mov 	dx, [EBX+DMonth]
   421 00006D97 8A1D[485B0100]      <1>         mov     bl, [day]
   422 00006D9D FECB                <1> 	dec 	bl
   423 00006D9F 01D0                <1> 	add 	eax, edx
   424 00006DA1 01D8                <1> 	add 	eax, ebx
   425                              <1> 			; EAX = days since 1/1/1970
   426 00006DA3 668B15[445B0100]    <1> 	mov 	dx, [year]
   427 00006DAA 6681EAB107          <1> 	sub 	dx, 1969
   428 00006DAF 66D1EA              <1> 	shr 	dx, 1
   429 00006DB2 66D1EA              <1> 	shr 	dx, 1		
   430                              <1> 		; (year-1969)/4
   431 00006DB5 01D0                <1> 	add 	eax, edx
   432                              <1> 			; + leap days since 1/1/1970
   433 00006DB7 803D[465B0100]02    <1> 	cmp 	byte [month], 2	; if past february
   434 00006DBE 7610                <1> 	jna 	short cte1
   435 00006DC0 668B15[445B0100]    <1> 	mov 	dx, [year]
   436 00006DC7 6683E203            <1> 	and 	dx, 3 ; year mod 4
   437 00006DCB 7503                <1> 	jnz 	short cte1		
   438                              <1> 			; and if leap year
   439 00006DCD 83C001              <1> 	add 	eax, 1 	; add this year's leap day (february 29)
   440                              <1> cte1: 			; compute seconds since 1/1/1970
   441 00006DD0 BA18000000          <1> 	mov 	edx, 24
   442 00006DD5 F7E2                <1> 	mul	edx
   443 00006DD7 8A15[4A5B0100]      <1> 	mov 	dl, [hour]
   444 00006DDD 01D0                <1> 	add 	eax, edx
   445                              <1> 		; EAX = hours since 1/1/1970 00:00:00
   446                              <1> 	;mov	ebx, 60
   447 00006DDF B33C                <1> 	mov	bl, 60
   448 00006DE1 F7E3                <1> 	mul	ebx
   449 00006DE3 8A15[4C5B0100]      <1> 	mov 	dl, [minute]
   450 00006DE9 01D0                <1> 	add 	eax, edx
   451                              <1> 		; EAX = minutes since 1/1/1970 00:00:00
   452                              <1> 	;mov 	ebx, 60
   453 00006DEB F7E3                <1> 	mul	ebx
   454 00006DED 8A15[4E5B0100]      <1> 	mov 	dl, [second]
   455 00006DF3 01D0                <1> 	add 	eax, edx
   456                              <1>  		; EAX -> seconds since 1/1/1970 00:00:00
   457 00006DF5 C3                  <1> 	retn
   458                              <1> 
   459                              <1> ;set_date_time:
   460                              <1> convert_from_epoch:
   461                              <1> 	; 31/12/2017 (v2.0.0)
   462                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0)
   463                              <1> 	; 15/03/2015 (Retro UNIX 386 v1 - 32 bit version)
   464                              <1> 	; 20/06/2013 (Retro UNIX 8086 v1)
   465                              <1> 	; 'convert_from_epoch' procedure prototype: 
   466                              <1> 	; 	            UNIXCOPY.ASM, 10/03/2013
   467                              <1> 	;
   468                              <1> 	; ((Modified registers: EAX, EDX, ECX, EBX))	
   469                              <1> 	;
   470                              <1> 	; Derived from DALLAS Semiconductor
   471                              <1> 	; Application Note 31 (DS1602/DS1603)
   472                              <1> 	; 6 May 1998
   473                              <1> 	;
   474                              <1> 	; INPUT:
   475                              <1> 	; EAX = Unix (Epoch) Time
   476                              <1> 	;
   477 00006DF6 31D2                <1> 	xor 	edx, edx
   478 00006DF8 B93C000000          <1> 	mov 	ecx, 60
   479 00006DFD F7F1                <1> 	div	ecx
   480                              <1> 	;mov 	[imin], eax   ; whole minutes
   481                              <1> 			  ; since 1/1/1970
   482 00006DFF 668915[4E5B0100]    <1> 	mov 	[second], dx  ; leftover seconds
   483 00006E06 29D2                <1> 	sub 	edx, edx
   484 00006E08 F7F1                <1> 	div	ecx
   485                              <1> 	;mov 	[ihrs], eax   ; whole hours
   486                              <1> 	;		      ; since 1/1/1970
   487 00006E0A 668915[4C5B0100]    <1> 	mov 	[minute], dx  ; leftover minutes
   488 00006E11 31D2                <1> 	xor	edx, edx
   489                              <1> 	;mov 	cx, 24
   490 00006E13 B118                <1> 	mov 	cl, 24
   491 00006E15 F7F1                <1> 	div	ecx
   492                              <1> 	;mov 	[iday], ax   ; whole days
   493                              <1> 			     ; since 1/1/1970
   494 00006E17 668915[4A5B0100]    <1> 	mov 	[hour], dx   ; leftover hours
   495 00006E1E 05DB020000          <1> 	add 	eax, 365+366 ; whole day since
   496                              <1> 			     ; 1/1/1968 	
   497                              <1> 	;mov 	[iday], ax
   498 00006E23 50                  <1> 	push 	eax
   499 00006E24 29D2                <1> 	sub	edx, edx
   500 00006E26 B9B5050000          <1> 	mov 	ecx, (4*365)+1 ; 4 years = 1461 days
   501 00006E2B F7F1                <1> 	div	ecx
   502 00006E2D 59                  <1> 	pop 	ecx
   503                              <1> 	;mov 	[lday], ax   ; count of quadyrs (4 years)
   504 00006E2E 6652                <1> 	push 	dx
   505                              <1> 	;mov 	[qday], dx   ; days since quadyr began
   506 00006E30 6683FA3C            <1> 	cmp 	dx, 31 + 29  ; if past feb 29 then
   507 00006E34 F5                  <1> 	cmc		     ; add this quadyr's leap day
   508 00006E35 83D000              <1> 	adc 	eax, 0	     ; to # of qadyrs (leap days)
   509                              <1> 	;mov 	[lday], ax   ; since 1968			  
   510                              <1> 	;mov 	cx, [iday]
   511 00006E38 91                  <1> 	xchg 	ecx, eax     ; ECX = lday, EAX = iday		  
   512 00006E39 29C8                <1> 	sub 	eax, ecx     ; iday - lday
   513 00006E3B B96D010000          <1> 	mov 	ecx, 365
   514 00006E40 31D2                <1> 	xor	edx, edx
   515                              <1> 	; EAX = iday-lday, EDX = 0
   516 00006E42 F7F1                <1> 	div	ecx
   517                              <1> 	;mov 	[iyrs], ax   ; whole years since 1968
   518                              <1> 	;jday = iday - (iyrs*365) - lday
   519                              <1> 	;mov [jday], dx      ; days since 1/1 of current year
   520                              <1> 	;add	eax, 1968
   521 00006E44 6605B007            <1> 	add 	ax, 1968     ; compute year
   522 00006E48 66A3[445B0100]      <1> 	mov 	[year], ax
   523 00006E4E 6689D1              <1> 	mov 	cx, dx
   524                              <1> 	;mov 	dx, [qday]
   525 00006E51 665A                <1> 	pop 	dx
   526 00006E53 6681FA6D01          <1> 	cmp 	dx, 365	     ; if qday <= 365 and qday >= 60	
   527 00006E58 7709                <1> 	ja 	short cfe1   ; jday = jday +1
   528 00006E5A 6683FA3C            <1> 	cmp 	dx, 60       ; if past 2/29 and leap year then
   529 00006E5E F5                  <1>         cmc		     ; add a leap day to the # of whole
   530 00006E5F 6683D100            <1> 	adc 	cx, 0        ; days since 1/1 of current year
   531                              <1> cfe1:			
   532                              <1> 	;mov 	[jday], cx
   533 00006E63 66BB0C00            <1> 	mov 	bx, 12       ; estimate month
   534 00006E67 66BA6E01            <1> 	mov 	dx, 366      ; mday, max. days since 1/1 is 365
   535 00006E6B 6683E003            <1> 	and 	ax, 11b      ; year mod 4 (and dx, 3) 
   536                              <1> cfe2:	; Month calculation  ; 0 to 11  (11 to 0)	
   537 00006E6F 6639D1              <1> 	cmp 	cx, dx       ; mday = # of days passed from 1/1
   538 00006E72 731D                <1> 	jnb 	short cfe3
   539 00006E74 664B                <1> 	dec 	bx           ; month = month - 1
   540 00006E76 66D1E3              <1> 	shl 	bx, 1 
   541 00006E79 668B93[505B0100]    <1> 	mov 	dx, [EBX+DMonth] ; # elapsed days at 1st of month
   542 00006E80 66D1EB              <1> 	shr 	bx, 1        ; bx = month - 1 (0 to 11)
   543 00006E83 6683FB01            <1> 	cmp	bx, 1        ; if month > 2 and year mod 4  = 0	
   544 00006E87 76E6                <1> 	jna 	short cfe2   ; then mday = mday + 1
   545 00006E89 08C0                <1> 	or 	al, al       ; if past 2/29 and leap year then
   546 00006E8B 75E2                <1> 	jnz 	short cfe2   ; add leap day (to mday)
   547 00006E8D 6642                <1> 	inc 	dx           ; mday = mday + 1
   548 00006E8F EBDE                <1> 	jmp 	short cfe2
   549                              <1> cfe3:
   550 00006E91 6643                <1> 	inc 	bx	     ; -> bx = month, 1 to 12
   551 00006E93 66891D[465B0100]    <1> 	mov 	[month], bx
   552 00006E9A 6629D1              <1> 	sub 	cx, dx	     ; day = jday - mday + 1	
   553 00006E9D 6641                <1> 	inc 	cx 			  
   554 00006E9F 66890D[485B0100]    <1> 	mov 	[day], cx
   555                              <1> 	
   556                              <1> 	; eax, ebx, ecx, edx is changed at return
   557                              <1> 	; output ->
   558                              <1> 	; [year], [month], [day], [hour], [minute], [second]
   559                              <1> 
   560 00006EA6 C3                  <1> 	retn	; 31/12/2017 (TRDOS 386)
   561                              <1> 
   562                              <1> set_rtc_date_time:
   563                              <1> 	; 31/12/2017 (v2.0.0)
   564                              <1> 	; 30/12/2017 (TRDOS 386)
   565                              <1> 	; 15/03/2015 (Retro UNIX 386 v1 - 32 bit version)
   566                              <1> 	; 20/06/2013 (Retro UNIX 8086 v1)
   567 00006EA7 E80F000000          <1> 	call	set_date_bcd
   568                              <1> 	; Set real-time clock date
   569 00006EAC E846F3FFFF          <1> 	call	set_rtc_date ; RTC_50
   570                              <1> 	; Set real-time clock time
   571 00006EB1 E832000000          <1> 	call	set_time_bcd
   572 00006EB6 E9CDF2FFFF          <1> 	jmp	set_rtc_time ; RTC_30	
   573                              <1> 
   574                              <1> ; 31/12/2017
   575                              <1> set_date_bcd:
   576 00006EBB A0[455B0100]        <1>         mov     al, [year+1]
   577 00006EC0 D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   578 00006EC2 D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   579                              <1> 			     ; AL = AH * 10h + AL
   580 00006EC4 88C5                <1> 	mov 	ch, al ; century (BCD)
   581 00006EC6 A0[445B0100]        <1> 	mov 	al, [year]
   582 00006ECB D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   583 00006ECD D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   584                              <1> 			     ; AL = AH * 10h + AL
   585 00006ECF 88C1                <1> 	mov 	cl, al ; year (BCD)
   586 00006ED1 A0[465B0100]        <1>         mov 	al, [month]
   587 00006ED6 D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   588 00006ED8 D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   589                              <1> 			     ; AL = AH * 10h + AL
   590 00006EDA 88C6                <1> 	mov 	dh, al ; month (BCD)
   591 00006EDC A0[485B0100]        <1> 	mov 	al, [day]
   592 00006EE1 D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   593 00006EE3 D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   594                              <1> 			     ; AL = AH * 10h + AL
   595 00006EE5 88C6                <1> 	mov 	dh, al ; day (BCD)
   596 00006EE7 C3                  <1> 	retn	; 30/12/2017
   597                              <1> 
   598                              <1> ; 31/12/2017
   599                              <1> set_time_bcd:
   600                              <1>         ; Read real-time clock time 
   601                              <1> 	; (get day light saving time bit status)
   602 00006EE8 FA                  <1>  	cli
   603 00006EE9 E85BF4FFFF          <1> 	CALL	UPD_IPR 		; CHECK FOR UPDATE IN PROCESS
   604                              <1> 	; cf = 1 -> al = 0
   605 00006EEE 7207                <1>         jc      short stime1
   606 00006EF0 B00B                <1> 	MOV	AL,CMOS_REG_B		; ADDRESS ALARM REGISTER
   607 00006EF2 E86DF4FFFF          <1> 	CALL	CMOS_READ		; READ CURRENT VALUE OF DSE BIT
   608                              <1> stime1:
   609 00006EF7 FB                  <1> 	sti
   610 00006EF8 2401                <1> 	AND	AL,00000001B		; MASK FOR VALID DSE BIT
   611 00006EFA 88C2                <1> 	MOV	DL,AL			; SET [DL] TO ZERO FOR NO DSE BIT
   612                              <1> 	; DL = 1 or 0 (day light saving time)
   613                              <1> 	;	
   614 00006EFC A0[4A5B0100]        <1> 	mov 	al, [hour]
   615 00006F01 D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   616 00006F03 D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   617                              <1> 			     ; AL = AH * 10h + AL
   618 00006F05 88C5                <1> 	mov 	ch, al ; hour (BCD)
   619 00006F07 A0[4C5B0100]        <1>         mov     al, [minute]
   620 00006F0C D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   621 00006F0E D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   622                              <1> 			     ; AL = AH * 10h + AL
   623 00006F10 88C1                <1> 	mov 	cl, al       ; minute (BCD)
   624 00006F12 A0[4E5B0100]        <1>         mov     al, [second]
   625 00006F17 D40A                <1> 	aam 	; ah = al / 10, al = al mod 10
   626 00006F19 D510                <1> 	db 	0D5h,10h     ; Undocumented inst. AAD
   627                              <1> 			     ; AL = AH * 10h + AL
   628 00006F1B 88C6                <1> 	mov 	dh, al	     ; second (BCD)
   629 00006F1D C3                  <1> 	retn	; 30/12/2017
  2862                                  %include 'trdosk2.s' ; 04/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.2) - DRV INIT : trdosk2.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 30/08/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 04/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.14 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; TRDOS2.ASM (09/11/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; DRV_INIT.ASM (c) 2009-2011 Erdogan TAN  [26/09/2009] Last Update: 07/08/2011
    14                              <1> ;
    15                              <1> 
    16                              <1> ldrv_init: ; Logical Drive Initialization
    17                              <1> 	; 30/08/2020
    18                              <1> 	; 25/08/2020
    19                              <1> 	; 11/08/2020, 13/08/2020
    20                              <1> 	; 17/07/2020, 20/07/2020
    21                              <1> 	; 14/07/2020, 15/07/2020
    22                              <1> 	; 30/01/2018
    23                              <1> 	; 27/12/2017
    24                              <1> 	; 12/02/2016
    25                              <1> 	; 06/01/2016
    26                              <1> 	;  	('diskinit.inc', 'diskio.inc' integration)
    27                              <1> 	; 04/01/2016 (TRDOS 386 = TRDOS v2.0)
    28                              <1> 	; 07/08/2011
    29                              <1> 	; 20/09/2009
    30                              <1> 	; 2005
    31                              <1> 
    32                              <1> 	; 15/07/2020
    33                              <1> 	;movzx	ecx, byte [HF_NUM] ; number of fixed disks
    34                              <1> 	;cmp	cl, 1
    35                              <1> 	;jnb	short load_hd_partition_tables
    36                              <1> 
    37 00006F1E A0[1C5F0100]        <1> 	mov	al, [HF_NUM] ; number of fixed disks
    38 00006F23 20C0                <1> 	and 	al, al
    39 00006F25 7501                <1> 	jnz	short load_hd_partition_tables
    40                              <1> 
    41                              <1> 	; no any hard disks
    42 00006F27 C3                  <1> 	retn			
    43                              <1> 
    44                              <1> load_hd_partition_tables:
    45                              <1> 	;mov	esi, [HDPM_TBL_VEC] ; primary master disk FDPT
    46                              <1> 	; 15/07/2020
    47 00006F28 BE[205F0100]        <1> 	mov	esi, HDPM_TBL_VEC
    48 00006F2D BF[46630100]        <1> 	mov 	edi, PTable_hd0
    49 00006F32 B280                <1> 	mov 	dl, 80h
    50                              <1> 	; 15/07/2020
    51 00006F34 A2[AD640000]        <1> 	mov	[hdc], al
    52                              <1> 	;xor	ecx, ecx ; 0
    53                              <1> load_next_hd_partition_table:
    54                              <1> 	; 20/07/2020
    55 00006F39 31C9                <1> 	xor	ecx, ecx ; 0
    56                              <1> 	;push	ecx
    57 00006F3B 57                  <1> 	push	edi ; *
    58                              <1> 	;push	esi ; FDPT (+ DPTE) address
    59                              <1> 	; 15/07/2020
    60 00006F3C AD                  <1> 	lodsd
    61 00006F3D 56                  <1> 	push	esi ; ** ; next FDPT (+ DPTE) address ptr
    62                              <1> 	
    63                              <1> 	;mov	al, [esi+20] ; DPTE offset 4
    64                              <1> 	;and	al, 40h ;  LBA bit (bit 6)
    65                              <1> 	;;shr	al, 6
    66                              <1> 	;mov 	[HD_LBA_yes], al
    67                              <1> 	
    68                              <1> 	; 15/07/2020
    69 00006F3E 8A4814              <1> 	mov	cl, [eax+20]
    70 00006F41 80E140              <1> 	and	cl, 40h
    71 00006F44 880D[4A640100]      <1> 	mov	[HD_LBA_yes], cl
    72                              <1> 	
    73 00006F4A E844040000          <1> 	call	load_masterboot
    74                              <1> 	;jc	short pass_pt_this_hard_disk
    75                              <1> 	; 13/08/2020
    76 00006F4F 0F828A000000        <1> 	jc	pass_pt_this_hard_disk
    77                              <1> 
    78 00006F55 BB[04630100]        <1> 	mov	ebx, PartitionTable
    79 00006F5A 89DE                <1> 	mov	esi, ebx
    80                              <1> 	;mov	ecx, 16
    81 00006F5C B110                <1> 	mov	cl, 16
    82 00006F5E F3A5                <1> 	rep 	movsd
    83 00006F60 89DE                <1> 	mov 	esi, ebx 
    84                              <1> 	;mov 	byte [hdc], 4 ; 4 - partition index
    85                              <1> 	; 15/07/2020
    86 00006F62 C605[4B640100]04    <1> 	mov	byte [PP_Counter], 4
    87                              <1> loc_validate_hdp_partition:
    88                              <1> 	;cmp 	byte [esi+ptFileSystemID], 0
    89                              <1> 	;jna	short loc_validate_next_hdp_partition2
    90                              <1> 	; 13/08/2020
    91 00006F69 8A4604              <1> 	mov	al, [esi+ptFileSystemID]
    92 00006F6C 20C0                <1> 	and	al, al
    93 00006F6E 7457                <1> 	jz	short loc_validate_next_hdp_partition2
    94                              <1> 
    95 00006F70 56                  <1> 	push	esi ; *** ; Masterboot partition table offset
    96 00006F71 52                  <1> 	push	edx ; **** ; dl = Physical drive number
    97                              <1> 
    98                              <1> 	; 13/08/2020
    99 00006F72 3C05                <1> 	cmp	al, 05h  ; Extended partition CHS
   100 00006F74 7404                <1>  	je	short loc_set_ep_counter
   101 00006F76 3C0F                <1> 	cmp	al, 0Fh  ; Extended partition LBA
   102 00006F78 7511                <1>  	jne	short loc_validate_next_hdp_partition0
   103                              <1> 	
   104                              <1> 	;;inc	byte [PP_Counter]
   105                              <1> 	; 15/07/2020
   106                              <1> 	;inc 	byte [EP_Counter] ; disk has valid partition(s)
   107                              <1> 
   108                              <1> loc_set_ep_counter:
   109                              <1> 	; 13/08/2020
   110 00006F7A 803D[4C640100]80    <1> 	cmp	byte [EP_Counter], 80h
   111 00006F81 7342                <1> 	jnb	short loc_validate_next_hdp_partition1
   112                              <1> 
   113 00006F83 8815[4C640100]      <1> 	mov	byte [EP_Counter], dl ; disk drv has extd. part.
   114                              <1> 
   115 00006F89 EB3A                <1> 	jmp	short loc_validate_next_hdp_partition1
   116                              <1> 
   117                              <1> loc_validate_next_hdp_partition0:
   118 00006F8B 31FF                <1> 	xor	edi, edi ; 0  
   119                              <1> 	; Input -> ESI = PartitionTable offset
   120                              <1> 	; DL = Hard disk drive number 
   121                              <1> 	; EDI = 0 -> Primary Partition
   122                              <1> 	; EDI > 0 -> Extended Partition's Start Sector   
   123 00006F8D E885010000          <1> 	call 	validate_hd_fat_partition
   124 00006F92 730E                <1> 	jnc 	short loc_set_valid_hdp_partition_entry
   125                              <1> 
   126                              <1> 	;pop	edx
   127                              <1> 	;push	edx
   128 00006F94 8B1424              <1> 	mov	edx, [esp]  ; ****
   129 00006F97 8B742404            <1> 	mov	esi, [esp+4] ; *** ; 30/01/2018
   130 00006F9B E8D1020000          <1> 	call	validate_hd_fs_partition
   131 00006FA0 7223                <1> 	jc	short loc_validate_next_hdp_partition1
   132                              <1> loc_set_valid_hdp_partition_entry:
   133 00006FA2 8A0D[C6120100]      <1> 	mov 	cl, [Last_DOS_DiskNo] 
   134 00006FA8 80C141              <1> 	add 	cl, 'A'
   135                              <1> 	; ESI = Logical dos drive description table address
   136 00006FAB 880E                <1> 	mov	[esi+LD_Name], cl
   137                              <1> 	; 15/07/2020
   138 00006FAD 8A4602              <1> 	mov	al, [esi+LD_PhyDrvNo] ; Physical drive number
   139                              <1> 	;mov	al, [esp] ; ****
   140 00006FB0 2C7F                <1> 	sub	al, 7Fh
   141                              <1> 		; AL = 1 to 4	
   142 00006FB2 C0E002              <1> 	shl	al, 2 ; AL = 4 to 16
   143                              <1> 
   144 00006FB5 8A15[4B640100]      <1> 	mov	dl, [PP_Counter]
   145                              <1> 
   146                              <1> 	;sub	al, [PP_Counter]
   147 00006FBB 28D0                <1> 	sub	al, dl ; [PP_Counter] ; 4 - partition index
   148                              <1> 
   149                              <1> 	; AL = Partition entry/index, 0 based
   150                              <1> 	;  0 -> hd 0, Partition Table offset = 0
   151                              <1> 	; 15 -> hd 3, Partition Table offset = 3
   152                              <1> 
   153                              <1> 	;mov	[esi+LD_PartitionEntry], al 
   154                              <1> 	
   155                              <1> 	; 15/07/2020
   156 00006FBD B404                <1> 	mov	ah, 4
   157                              <1> 	;sub	ah, [PP_Counter]
   158 00006FBF 28D4                <1> 	sub	ah, dl
   159                              <1> 
   160                              <1> 	; AH = Primary partition index, 0 to 3 ; pt entry
   161                              <1> 	;		(4 to 7 for logical disk partitions)
   162                              <1> 
   163                              <1> 	;mov 	[esi+LD_DParamEntry], ah 
   164 00006FC1 6689467C            <1> 	mov 	[esi+LD_PartitionEntry], ax
   165                              <1> 
   166                              <1> loc_validate_next_hdp_partition1:
   167 00006FC5 5A                  <1> 	pop 	edx ; **** ; dl = Physical drive number 
   168 00006FC6 5E                  <1> 	pop	esi ; *** ; Masterboot partition table offset
   169                              <1> 
   170                              <1> loc_validate_next_hdp_partition2:
   171                              <1> 	; ESI = PartitionTable offset
   172                              <1> 	; DL = Hard/Fixed disk drive number
   173                              <1> 	
   174                              <1> 	;dec	byte [hdc] ; 4 - partition index
   175                              <1> 	;jz	short pass_pt_this_hard_disk
   176                              <1> 	; 15/07/2020
   177 00006FC7 FE0D[4B640100]      <1> 	dec	byte [PP_Counter] ; 4 - partition index
   178 00006FCD 7410                <1> 	jz	short pass_pt_this_hard_disk
   179                              <1> 	
   180 00006FCF 83C610              <1> 	add	esi, 16 ; 10h
   181 00006FD2 EB95                <1> 	jmp	short loc_validate_hdp_partition
   182                              <1> 
   183                              <1> loc_not_any_extd_partitions:
   184                              <1> 	; 15/07/2020
   185 00006FD4 C3                  <1> 	retn	
   186                              <1> 
   187                              <1> loc_next_hd_partition_table:
   188 00006FD5 FEC2                <1> 	inc	dl
   189                              <1> 	; 15/07/2020
   190                              <1> 	;add	esi, 32 ; next FDPT address
   191 00006FD7 83C740              <1> 	add	edi, 64 ; next partition table destination
   192 00006FDA E95AFFFFFF          <1>         jmp     load_next_hd_partition_table
   193                              <1> 
   194                              <1> pass_pt_this_hard_disk:
   195                              <1> 	;pop	esi ; FDPT (+ DPTE) address
   196                              <1> 	; 15/07/2020
   197 00006FDF 5E                  <1> 	pop	esi ; ** ; next FDPT (+ DPTE) address ptr
   198 00006FE0 5F                  <1> 	pop	edi ; * ; Ptable_hd?
   199                              <1> 	;pop	ecx
   200                              <1> 	;loop	loc_next_hd_partition_table
   201 00006FE1 FE0D[AD640000]      <1> 	dec	byte [hdc]
   202 00006FE7 75EC                <1> 	jnz	short loc_next_hd_partition_table
   203                              <1> 
   204                              <1> 	;cmp	byte [PP_Counter], 1
   205                              <1> 	;jnb	short load_extended_dos_partitions
   206                              <1> 	;; Empty partition table
   207                              <1> 	;retn
   208                              <1> 
   209                              <1> 	; 11/08/2020
   210                              <1> 	; 17/07/2020
   211                              <1> check_extended_partitions:
   212                              <1> 	; 15/07/2020
   213                              <1> 	;cmp	byte [EP_Counter], 0
   214                              <1> 	;jna	short loc_not_any_extd_partitions
   215                              <1> 	; 13/08/2020
   216 00006FE9 A0[4C640100]        <1> 	mov	al, [EP_Counter] ; 1st disk drv has extd partition
   217 00006FEE 08C0                <1> 	or	al, al ; 0 ?
   218 00006FF0 74E2                <1> 	jz	short loc_not_any_extd_partitions
   219                              <1> 
   220                              <1> load_extended_dos_partitions:
   221                              <1> 	;mov	byte [hdc], 80h
   222                              <1> 	; 13/08/2020
   223 00006FF2 A2[AD640000]        <1> 	mov	byte [hdc], al ; 1st disk drv has extd partition
   224                              <1> 	; 25/08/2020
   225 00006FF7 2C80                <1> 	sub	al, 80h
   226 00006FF9 740E                <1> 	jz	short loc_set_ext_ptable_hd0
   227 00006FFB C0E006              <1> 	shl	al, 6 ; * 64
   228 00006FFE 0FB6F0              <1> 	movzx	esi, al
   229 00007001 81C6[46630100]      <1> 	add	esi, PTable_hd0
   230 00007007 EB05                <1> 	jmp 	short next_hd_extd_partition
   231                              <1> 
   232                              <1> 	; 25/08/2020
   233                              <1> loc_set_ext_ptable_hd0:
   234 00007009 BE[46630100]        <1> 	mov	esi, PTable_hd0
   235                              <1> 
   236                              <1> next_hd_extd_partition:
   237                              <1> 	; 17/07/2020
   238                              <1> 	;mov 	byte [EP_Counter], 0 ; Reset for each physical disk
   239                              <1> 	; 13/08/2020
   240                              <1> 	;mov	byte [LD_Counter], 0 ; Reset logical drive index
   241 0000700E 66C705[4C640100]00- <1> 	mov 	word [EP_Counter], 0 ; Reset EP index and LD index	
   241 00007016 00                  <1>
   242                              <1> 
   243 00007017 56                  <1> 	push	esi ; **** ; PTable_hd? offset
   244                              <1> 	
   245 00007018 C605[4B640100]04    <1> 	mov 	byte [PP_Counter], 4 
   246                              <1> 				; set for each extd partition table
   247                              <1> 	;;mov	ecx, 4
   248                              <1> 	;mov	cl, 4
   249 0000701F 8A15[AD640000]      <1> 	mov	dl, [hdc]
   250                              <1> hd_check_fs_id_05h:
   251 00007025 8A4604              <1> 	mov	al, [esi+ptFileSystemID]
   252 00007028 3C05                <1> 	cmp	al, 05h ; Is it an extended dos partition ?
   253 0000702A 7411                <1> 	je	short loc_set_ep_start_sector ; yes
   254                              <1> hd_check_fs_id_0Fh:
   255 0000702C 3C0F                <1> 	cmp	al, 0Fh ; Is it an extended win4 (LBA mode) partition ?
   256 0000702E 740D                <1> 	je	short loc_set_ep_start_sector ; yes
   257                              <1> 
   258                              <1> continue_to_check_ep:
   259                              <1> 	;add	esi, 16
   260                              <1> 	;loop	hd_check_fs_id_05h
   261                              <1> 	; 15/07/2020
   262                              <1> 	;dec	cl
   263                              <1> 	;jz	short continue_check_ep_next_disk
   264 00007030 FE0D[4B640100]      <1> 	dec	byte [PP_Counter] ; 4 --> 0
   265 00007036 742D                <1> 	jz	short continue_check_ep_next_disk
   266 00007038 83C610              <1> 	add	esi, 16
   267 0000703B EBE8                <1> 	jmp	short hd_check_fs_id_05h
   268                              <1> 
   269                              <1> loc_set_ep_start_sector:
   270                              <1> 	; dl = [hdc] ; Drive number
   271                              <1> 	; 15/07/2020
   272 0000703D 8B4E08              <1> 	mov	ecx, [esi+ptStartSector]
   273                              <1> 	; 30/08/2020
   274 00007040 890D[4E640100]      <1> 	mov	[MBR_EP_StartSector], ecx 
   275                              <1> 	; 20/07/2020
   276                              <1> loc_validate_hde_partition_next:
   277 00007046 890D[52640100]      <1> 	mov	[EP_StartSector], ecx ; Extended partition's start sector
   278 0000704C BB[46610100]        <1>         mov	ebx, MasterBootBuff
   279 00007051 803D[4A640100]01    <1> 	cmp	byte [HD_LBA_yes], 1 ; LBA ready = Yes
   280 00007058 7227                <1> 	jb	short loc_hd_load_ep_05h ; cf = 1 ; 20/07/2020 
   281                              <1> 	; 11/08/2020
   282                              <1> 	; (BugFix for extended partition type 05h beyond CHS limit)
   283                              <1> 	; (Infact if extended partition starts at the beyond of CHS limit,
   284                              <1> 	;  it's partition ID must be 0Fh but they/somebodies had used 05h.)
   285                              <1> 	;cmp	al, 05h
   286                              <1> 	;je	short loc_hd_load_ep_05h
   287                              <1> loc_hd_load_ep_0Fh:
   288                              <1> 	; 04/01/2016
   289                              <1> 	;push	ecx
   290                              <1> 	; 15/07/2020
   291                              <1> 	;mov	ecx, [esi+ptStartSector] ; sector number
   292                              <1> 	;mov	ebx, MasterBootBuff ; buffer address
   293                              <1> 	; LBA read/write (with private LBA function) 
   294                              <1> 	;((Retro UNIX 386 v1 - DISK I/O code by Erdogan Tan))
   295                              <1> 	; dl = physical drive number (0,1, 80h, 81h, 82h, 83h)
   296                              <1> 	;mov	ah, 1Bh ; LBA read
   297                              <1> 	;mov	al, 1 ; sector count
   298 0000705A 66B8011B            <1> 	mov	ax, 1B01h
   299 0000705E E8D8D8FFFF          <1> 	call	int13h
   300                              <1> 	;pop	ecx
   301                              <1> 	;jnc	short loc_hd_move_ep_table
   302                              <1> 	; 15/07/2020
   303 00007063 732E                <1> 	jnc	short loc_validate_hde_partition
   304                              <1> 
   305                              <1> continue_check_ep_next_disk:
   306                              <1> 	; 15/07/2020
   307                              <1> 	;pop	edi ; PTable_ep?
   308 00007065 5E                  <1> 	pop	esi ; **** ; PTable_hd?
   309 00007066 A0[1C5F0100]        <1> 	mov	al, [HF_NUM] ; number of hard disks
   310 0000706B 047F                <1> 	add	al, 7Fh
   311 0000706D 3805[AD640000]      <1> 	cmp	[hdc], al
   312 00007073 730B                <1> 	jnb	short loc_validating_hd_partitions_ok
   313 00007075 83C640              <1> 	add	esi, 64
   314                              <1> 	; 15/07/2020
   315                              <1> 	;add	edi, 64
   316 00007078 FE05[AD640000]      <1> 	inc	byte [hdc]
   317 0000707E EB8E                <1> 	jmp	short next_hd_extd_partition
   318                              <1> 
   319                              <1> loc_validating_hd_partitions_ok:
   320                              <1> 	; 15/07/2020
   321                              <1> 	;mov	al, [Last_DOS_DiskNo]
   322                              <1> loc_drv_init_retn:
   323 00007080 C3                  <1> 	retn
   324                              <1> 	
   325                              <1> loc_hd_load_ep_05h:
   326                              <1> 	; 20/07/2020 ('diskio.s', int13h, cf = 1 -> bugfix)
   327                              <1> 	;clc    ; (Bug: int13h would not clear carry flag bit, 
   328                              <1> 	;	; even if there would not be an error)
   329                              <1> 	;	; ((Fix: now, int13h procedure clears carry flag
   330                              <1> 	;	;  at the entrance of it.. 20/07/2020))
   331                              <1> 	; 15/07/2020
   332                              <1> 	;push	ecx 
   333 00007081 8A7601              <1> 	mov	dh, [esi+ptBeginHead]
   334 00007084 668B4E02            <1>         mov     cx, [esi+ptBeginSector]
   335 00007088 66B80102            <1> 	mov	ax, 0201h ; Read 1 sector
   336                              <1> 	;mov	ebx, MasterBootBuff
   337 0000708C E8AAD8FFFF          <1> 	call	int13h ; 20/07/2020
   338                              <1> 		       ; 'diskio.s' modification, 'clc'
   339                              <1> 	;pop	ecx  
   340 00007091 72D2                <1> 	jc	short continue_check_ep_next_disk
   341                              <1> 	; 15/07/2020
   342                              <1> 	;jmp	short loc_validate_hde_partition
   343                              <1> 
   344                              <1> 	; 15/07/2020
   345                              <1> ;loc_hd_move_ep_table:
   346                              <1> 	;;pop	edi
   347                              <1> 	;;push	edi  ; PTable_ep?
   348                              <1> 	;mov	edi, [esp]        
   349                              <1>         ;mov	esi, PartitionTable ; Extended
   350                              <1> 	;mov	ebx, esi
   351                              <1> 	;;mov	ecx, 16
   352                              <1> 	;mov	cl, 16
   353                              <1>        	;rep	movsd
   354                              <1> 	;mov	esi, ebx 
   355                              <1> ;loc_set_hde_sub_partition_count:
   356                              <1> 	;mov	byte [PP_Counter], 4
   357                              <1> 	;mov	byte [EP_Counter], 0
   358                              <1> 
   359                              <1> loc_validate_hde_partition:
   360                              <1> 	; 13/08/2020
   361                              <1> 	; 15/07/2020
   362                              <1> 	;mov	byte [PP_Counter], 4
   363 00007093 BE[04630100]        <1> 	mov	esi, PartitionTable ; (in MasterBootBuff)
   364                              <1> 	; 13/08/2020
   365                              <1> 	;jmp	short get_minidisk_partition_entry
   366                              <1> 
   367                              <1> ;get_minidisk_partition_entry:
   368                              <1> ;	; 20/07/2020
   369                              <1> ;	cmp	byte [esi+ptFileSystemID], 0
   370                              <1> ;	ja	short loc_validate_minidisk_partition
   371                              <1> ;	; 13/08/2020
   372                              <1> ;	jmp	short continue_check_ep_next_disk
   373                              <1> 
   374                              <1> ;	; 11/08/2020
   375                              <1> ;get_minidisk_partition_entry_next:
   376                              <1> ;	; 13/08/2020
   377                              <1> ;	;dec 	byte [PP_Counter]
   378                              <1> ;	;jz	short continue_check_ep_next_disk
   379                              <1> ;	; 20/07/2020
   380                              <1> ;;get_minidisk_partition_entry_next:
   381                              <1> ;	; 13/08/2020
   382                              <1> ;	cmp	esi, PartitionTable+64 
   383                              <1> ;	jnb	short continue_check_ep_next_disk
   384                              <1> ;	
   385                              <1> ;	add 	esi, 16 ; 10h
   386                              <1> ;	;jmp	short get_minidisk_partition_entry
   387                              <1> 
   388                              <1> 	; 13/08/2020
   389                              <1> get_minidisk_partition_entry:
   390                              <1> 	; 20/07/2020
   391 00007098 807E0400            <1> 	cmp	byte [esi+ptFileSystemID], 0
   392 0000709C 76C7                <1> 	jna	short continue_check_ep_next_disk ; 13/08/2020
   393                              <1> 
   394                              <1> loc_validate_minidisk_partition:
   395                              <1> 	; 13/08/2020
   396                              <1> 	; 20/07/2020
   397                              <1> 	;push	esi ; *** ; Extended partition table offset
   398                              <1> 
   399                              <1> 	; 13/08/2020
   400 0000709E FE05[4C640100]      <1> 	inc	byte [EP_Counter] ; current (sub partition) index 
   401                              <1> 				  ; in current extended partition
   402                              <1> 
   403 000070A4 BF[52640100]        <1> 	mov	edi, EP_StartSector
   404                              <1> 
   405                              <1> 	; Input -> ESI = PartitionTable offset
   406                              <1> 	; DL = Hard disk drive number   
   407                              <1> 	; EDI = Extended partition start sector pointer
   408 000070A9 E869000000          <1> 	call	validate_hd_fat_partition
   409                              <1> 	;pop	ecx ; *
   410 000070AE 7308                <1> 	jnc	short loc_set_valid_hde_partition_entry
   411                              <1> 			 ; jump down to deep !!!
   412                              <1> 
   413                              <1> 	;pop	esi ; *** ; Extended partition table offset
   414                              <1> 	; 13/08/2020
   415                              <1> 	;mov	esi, PartitionTable
   416                              <1> 
   417                              <1> 	; 11/08/2020
   418                              <1> 	; ESI = Extended partition table offset
   419 000070B0 8A15[AD640000]      <1> 	mov	dl, [hdc]
   420                              <1> 
   421                              <1> 	;; DL = Hard disk drive number
   422                              <1> 	;dec	byte [PP_Counter]
   423                              <1> 	;jz	short continue_check_ep_next_disk
   424                              <1> 	;add 	esi, 16 ; 10h
   425                              <1> 	;mov	dl, [hdc]
   426                              <1> 	;jmp	short get_minidisk_partition_entry
   427                              <1> 
   428                              <1> 	; 11/08/2020
   429                              <1> 	;jmp	short get_minidisk_partition_entry_next
   430                              <1> 
   431                              <1> 	; 23/08/2020
   432 000070B6 EB3D                <1> 	jmp	short validate_next_minidisk_partition_ok
   433                              <1> 
   434                              <1> 	; 17/07/2020
   435                              <1> 	;; jumping down to deep levels !!!
   436                              <1> 	; ((That is a pitty microsoft preferred ep table chain
   437                              <1> 	; instead of a single table as mbr partition table!?))
   438                              <1> 
   439                              <1> loc_set_valid_hde_partition_entry:
   440                              <1> 	; 15/07/2020
   441 000070B8 A0[AD640000]        <1> 	mov	al, [hdc] ; Hard disk drive number (>=80h)
   442 000070BD 88C2                <1> 	mov	dl, al ; mov dl, [hdc]
   443 000070BF 2C7F                <1> 	sub	al, 7Fh
   444                              <1> 		    ; 1 to 4	
   445 000070C1 C0E002              <1> 	shl	al, 2 ; 4 to 16
   446 000070C4 2A05[4B640100]      <1> 	sub	al, [PP_Counter] ; al - (4 - partition index)
   447                              <1> 			; (disk number * 4) + partition index
   448                              <1> 	
   449                              <1> 	; AL = Partition entry/index, 0 based
   450                              <1>         ;  0 -> hd 0, Partition Table offset = 0
   451                              <1>         ; 15 -> hd 3, Partition Table offset = 3
   452                              <1> 
   453                              <1> 	;mov	ah, 4 ; Logical dos partition (>= 4)
   454                              <1> 	;add	ah, [EP_Counter]
   455                              <1> 		; Logical disk partition index = 4 to 7
   456                              <1> 		; (Primary disk partition index = 0 to 3)
   457                              <1> 
   458                              <1> 	; 13/08/2020
   459 000070CA 8A25[4D640100]      <1> 	mov	ah, [LD_Counter] ; Logical drive index number
   460                              <1> 				; (in current extended partition)
   461 000070D0 80C404              <1> 	add	ah, 4 ; 4 to 7
   462                              <1> 	
   463                              <1> 	; 15/07/2020
   464                              <1> 	; CX -> AX
   465                              <1> 	;; 06/01/2016 (TRDOS v2.0)
   466                              <1> 	;; BUGFIX *
   467                              <1> 	;;mov	[esi+LD_PartitionEntry], cl 
   468                              <1> 	;;mov	[esi+LD_DParamEntry], ch 
   469                              <1> 	;mov	[esi+LD_PartitionEntry], cx 
   470 000070D3 6689467C            <1> 	mov	[esi+LD_PartitionEntry], ax 	
   471                              <1> 
   472 000070D7 8A0D[C6120100]      <1> 	mov	cl, [Last_DOS_DiskNo] 
   473 000070DD 80C141              <1> 	add	cl, 'A'
   474 000070E0 880E                <1> 	mov	[esi+LD_Name], cl
   475                              <1> 
   476                              <1> 	; 17/07/2020
   477                              <1> 	;cmp	cl, 'Z'
   478                              <1> 	;jb	short logical_drive_count_ok_for_next
   479                              <1> 	;pop	esi ; ***
   480                              <1> 	;pop	esi ; ****
   481                              <1> 	;retn
   482                              <1> 
   483                              <1> ;logical_drive_count_ok_for_next:
   484                              <1> 
   485                              <1> 	;; 15/07/2020
   486                              <1> 	;inc	byte [EP_Counter]
   487                              <1> 	; 13/08/2020
   488 000070E2 FE05[4D640100]      <1> 	inc	byte [LD_Counter]	
   489                              <1> 
   490                              <1> 	;mov	dl, [hdc]
   491                              <1> 
   492                              <1> 	; 17/07/2020
   493                              <1> 	;; Now, 
   494                              <1> 	;; we are swimming in deep of an extended partition !!!
   495                              <1> 	; (! sub or chained extended partition tables !)
   496                              <1> 	; ((Logical dos partitions in extended partition were called
   497                              <1> 	;  as 'mini disk partition' in msdos 6.0 source code.))
   498                              <1> 
   499                              <1> validate_next_minidisk_partition:
   500                              <1> 	; 13/08/2020
   501                              <1> 	;pop	esi ; *** ; Extended partition table offset
   502                              <1> 
   503                              <1> 	; 17/07/2020
   504                              <1> 	;cmp	byte [EP_Counter], 4
   505                              <1> 	; 13/08/2020
   506 000070E8 803D[4D640100]04    <1> 	cmp	byte [LD_Counter], 4 ; maximum 4 logical disks
   507                              <1> 				     ; per extended partition
   508 000070EF 0F8370FFFFFF        <1> 	jnb	continue_check_ep_next_disk
   509                              <1> 
   510                              <1> validate_next_minidisk_partition_ok:
   511                              <1> 	; 13/08/2020
   512                              <1> 	;dec	byte [PP_Counter] ; 4 --> 0
   513                              <1> 	;jz	continue_check_ep_next_disk
   514                              <1> 	
   515                              <1> 	;cmp	esi, PartitionTable+64 
   516                              <1> 	;jnb	continue_check_ep_next_disk
   517                              <1> 
   518                              <1> 	;add	esi, 16
   519                              <1> 	; 13/08/2020
   520 000070F5 BE[14630100]        <1> 	mov	esi, PartitionTable+16
   521                              <1> 
   522                              <1> 	; 20/07/2020
   523 000070FA 8A4604              <1> 	mov	al, [esi+ptFileSystemID]
   524                              <1> 
   525                              <1> 	; 20/07/2020
   526 000070FD 3C05                <1> 	cmp	al, 05h ; Is it an extended dos partition ?
   527 000070FF 7408                <1> 	je	short loc_minidisk_next_ep_lba_chs ; 17/07/2020
   528 00007101 3C0F                <1> 	cmp	al, 0Fh ; Is it an extended win4 (LBA mode) partition ?
   529 00007103 0F855CFFFFFF        <1> 	jne	continue_check_ep_next_disk ; AL must be 0 here
   530                              <1> 					; (when it is not 05h or 0Fh)
   531                              <1> 					; If AL is not ZERO -> EP Bug!
   532                              <1> 					; (!Microsoft DOS convention!)
   533                              <1> loc_minidisk_next_ep_lba_chs:
   534                              <1> 	; 17/07/2020
   535 00007109 8B4E08              <1> 	mov	ecx, [esi+ptStartSector] ; relative start sector number
   536                              <1> 	;add	ecx, [EP_StartSector]
   537                              <1> 	; 30/08/2020	
   538 0000710C 030D[4E640100]      <1> 	add	ecx, [MBR_EP_StartSector] 
   539                              <1> 	; 20/07/2020
   540 00007112 E92FFFFFFF          <1> 	jmp	loc_validate_hde_partition_next
   541                              <1> 
   542                              <1> validate_hd_fat_partition:
   543                              <1> 	; 17/07/2020
   544                              <1> 	; 15/07/2020
   545                              <1> 	;	(optimization)
   546                              <1> 	; 14/07/2020
   547                              <1> 	;	(fat16 -big- partition search bugfix)
   548                              <1> 	; 27/12/2017
   549                              <1> 	; 12/02/2016
   550                              <1> 	; 07/01/2016 (TRDOS 386 = TRDOS v2.0)
   551                              <1> 	; 07/08/2011
   552                              <1> 	; 23/07/2011
   553                              <1> 	; Input
   554                              <1> 	;   DL = Hard/Fixed Disk Drive Number
   555                              <1> 	;   ESI = PartitionTable offset
   556                              <1> 	;   EDI = Extend. Part. Start Sector Pointer
   557                              <1> 	;   EDI = 0 -> Primary Partition 
   558                              <1> 	;   byte [Last_DOS_DiskNo]
   559                              <1>  	; Output
   560                              <1> 	;  cf=0 -> Validated
   561                              <1> 	;   ESI = Logical dos drv desc. table
   562                              <1> 	;   EBX = FAT boot sector buffer
   563                              <1> 	;   byte [Last_DOS_DiskNo]
   564                              <1> 	;  cf=1 -> Not a valid FAT partition
   565                              <1> 	; EAX, EDX, ECX, EDI -> changed 
   566                              <1> 	
   567                              <1> 	;mov 	esi, PartitionTable
   568 00007117 8A6604              <1> 	mov 	ah, [esi+ptFileSystemID]
   569 0000711A B002                <1> 	mov	al, 2 ; 27/12/2017
   570 0000711C 80FC06              <1> 	cmp 	ah, 06h ; FAT16 CHS partition (>=32MB)
   571                              <1> 	; 12/02/2016
   572                              <1> 	;;jb	short loc_not_a_valid_fat_partition2
   573                              <1>  	;jnb	short vhdp_FAT16_32
   574                              <1> 	; 14/07/2020 (BugFix)
   575 0000711F 7711                <1> 	ja	short vhdp_FAT16_32
   576 00007121 7425                <1> 	je	short loc_set_valid_hd_partition_params
   577                              <1> 
   578                              <1> vhdp_FAT12_16:
   579                              <1> 	; 27/12/2017
   580 00007123 FEC8                <1> 	dec	al ; mov al, 1
   581 00007125 38C4                <1> 	cmp	ah, al ; 1 ; FAT12 partition
   582 00007127 741F                <1> 	je	short loc_set_valid_hd_partition_params
   583                              <1> 	;
   584 00007129 FEC0                <1> 	inc	al ; mov al, 2
   585 0000712B 80FC04              <1> 	cmp	ah, 04h ; FAT16 CHS partition (< 32MB)
   586 0000712E 7418                <1> 	je	short loc_set_valid_hd_partition_params
   587                              <1> 	
   588                              <1> 	; 15/07/2020
   589                              <1> 	; (ah = 05h, 02h or 03h)
   590                              <1> loc_not_a_valid_fat_partition1:
   591 00007130 F9                  <1> 	stc
   592                              <1> 	; cf=1
   593 00007131 C3                  <1> 	retn
   594                              <1> 
   595                              <1> vhdp_FAT16_32:
   596                              <1> 	; 15/07/2020
   597                              <1> 	;mov	al, 3
   598 00007132 FEC0                <1> 	inc	al
   599 00007134 80FC0C              <1> 	cmp	ah, 0Ch ; FAT32 LBA partition
   600 00007137 740F                <1> 	je	short loc_set_valid_hd_partition_params
   601 00007139 7706                <1> 	ja	short vhdp_check_FAT16_lba
   602                              <1> 
   603                              <1> vhdp_check_FAT32_chs:
   604 0000713B 80FC0B              <1> 	cmp	ah, 0Bh ; FAT32 CHS partition 
   605 0000713E 7408                <1> 	je	short loc_set_valid_hd_partition_params
   606                              <1> 	;jne	short loc_not_a_valid_fat_partition1
   607                              <1> 
   608                              <1> 	;stc
   609                              <1> loc_not_a_valid_fat_partition2:
   610 00007140 C3                  <1> 	retn
   611                              <1> 
   612                              <1> vhdp_check_FAT16_lba:
   613 00007141 80FC0E              <1> 	cmp	ah, 0Eh ; FAT16 LBA partition
   614 00007144 75EA                <1> 	jne	short loc_not_a_valid_fat_partition1
   615                              <1> 
   616                              <1> 	;mov	al, 2
   617 00007146 FEC8                <1> 	dec	al
   618                              <1> 
   619                              <1> loc_set_valid_hd_partition_params:
   620                              <1> 	; 15/07/2020
   621                              <1> 	;inc 	byte [Last_DOS_DiskNo] ; > 1
   622                              <1> 	;
   623 00007148 31DB                <1> 	xor	ebx, ebx
   624 0000714A 8A3D[C6120100]      <1> 	mov	bh, [Last_DOS_DiskNo] ; * 256	
   625 00007150 FEC7                <1> 	inc	bh ; 15/07/2020
   626 00007152 81C300010900        <1> 	add	ebx, Logical_DOSDisks
   627                              <1> 	;
   628 00007158 C6430102            <1> 	mov	byte [ebx+LD_DiskType], 2
   629 0000715C 885302              <1> 	mov	byte [ebx+LD_PhyDrvNo], dl
   630                              <1> 	;mov	byte [ebx+LD_FATType], al ; 2 or 3
   631                              <1> 	;mov	byte [ebx+LD_FSType], ah ; 06h, 0Eh, 0Bh, 0Ch
   632 0000715F 66894303            <1> 	mov	word [ebx+LD_FATType], ax
   633                              <1> 	;
   634 00007163 8B4E08              <1> 	mov	ecx, [esi+ptStartSector]
   635 00007166 09FF                <1> 	or	edi, edi 
   636 00007168 7402                <1> 	jz	short pass_hd_FAT_ep_start_sector_adding
   637                              <1> loc_add_hd_FAT_ep_start_sector:
   638                              <1> 	; 17/07/2020
   639 0000716A 030F                <1> 	add	ecx, [edi]
   640                              <1> pass_hd_FAT_ep_start_sector_adding:
   641 0000716C 894B6C              <1> 	mov	[ebx+LD_StartSector], ecx
   642                              <1> loc_hd_FAT_logical_drv_init:
   643 0000716F 89DD                <1> 	mov	ebp, ebx
   644                              <1> 	;mov	dl, [ebx+LD_PhyDrvNo]
   645 00007171 A0[4A640100]        <1> 	mov	al, [HD_LBA_yes] ; 07/01/2016
   646 00007176 884305              <1> 	mov	[ebx+LD_LBAYes], al
   647 00007179 BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff ; buffer address
   648 0000717E 08C0                <1> 	or	al, al
   649 00007180 740C                <1> 	jz	short loc_hd_FAT_drv_init_load_bs_chs
   650                              <1> loc_hd_FAT_drv_init_load_bs_lba:
   651                              <1> 	; DL = Physical drive number
   652                              <1>    	;mov	ecx, [esi+ptStartSector] ; sector number
   653                              <1> 	;mov	ebx, DOSBootSectorBuff ; buffer address
   654                              <1> 	; LBA read/write (with private LBA function) 
   655                              <1> 	;((Retro UNIX 386 v1 - DISK I/O code by Erdogan Tan))
   656                              <1> 	; dl = physical drive number (0,1, 80h, 81h, 82h, 83h)
   657 00007182 B41B                <1> 	mov	ah, 1Bh ; LBA read
   658 00007184 B001                <1> 	mov	al, 1 ; sector count
   659 00007186 E8B0D7FFFF          <1> 	call	int13h
   660 0000718B 7313                <1> 	jnc	short loc_hd_drv_FAT_boot_validation
   661                              <1> loc_not_a_valid_fat_partition3:
   662 0000718D C3                  <1> 	retn
   663                              <1> loc_hd_FAT_drv_init_load_bs_chs:
   664 0000718E 8A7601              <1> 	mov	dh, [esi+ptBeginHead]
   665 00007191 668B4E02            <1> 	mov	cx, [esi+ptBeginSector]
   666 00007195 66B80102            <1> 	mov	ax, 0201h ; Read 1 sector
   667                              <1> 	;mov	ebx, DOSBootSectorBuff
   668 00007199 E89DD7FFFF          <1> 	call	int13h
   669 0000719E 72ED                <1> 	jc	short loc_not_a_valid_fat_partition3
   670                              <1> loc_hd_drv_FAT_boot_validation:
   671                              <1> 	;mov	esi, DOSBootSectorBuff
   672 000071A0 89DE                <1> 	mov	esi, ebx
   673 000071A2 6681BEFE01000055AA  <1> 	cmp	word [esi+BS_Validation], 0AA55h
   674 000071AB 7512                <1> 	jne	short loc_not_a_valid_fat_partition4
   675 000071AD 807E15F8            <1> 	cmp	byte [esi+BPB_Media], 0F8h
   676 000071B1 750C                <1> 	jne	short loc_not_a_valid_fat_partition4
   677                              <1> 
   678                              <1> 	; 27/12/2017
   679 000071B3 807D0303            <1> 	cmp	byte [ebp+LD_FATType], 3
   680 000071B7 7508                <1> 	jne	short loc_hd_FAT16_BPB
   681                              <1> 
   682                              <1> loc_hd_drv_FAT32_boot_validation:
   683 000071B9 807E4229            <1> 	cmp	byte [esi+BS_FAT32_BootSig], 29h
   684 000071BD 7416                <1> 	je	short loc_hd_FAT32_BPB
   685                              <1> 
   686                              <1> loc_not_a_valid_fat_partition4:
   687 000071BF F9                  <1> 	stc
   688 000071C0 C3                  <1> 	retn
   689                              <1> 
   690                              <1> loc_hd_FAT16_BPB:
   691 000071C1 807E2629            <1> 	cmp	byte [esi+BS_BootSig], 29h
   692 000071C5 75F8                <1> 	jne	short loc_not_a_valid_fat_partition4
   693                              <1> 
   694 000071C7 66837E1600          <1> 	cmp	word [esi+BPB_FATSz16], 0
   695 000071CC 7607                <1> 	jna	short loc_hd_big_FAT16_BPB
   696 000071CE B920000000          <1> 	mov	ecx, 32
   697 000071D3 EB05                <1> 	jmp	short loc_hd_move_FAT_BPB
   698                              <1> 
   699                              <1> loc_hd_FAT32_BPB:
   700                              <1> 	;cmp	word [esi+BPB_FATSz16], 0
   701                              <1> 	;ja	short loc_not_a_valid_fat_partition4
   702                              <1> loc_hd_big_FAT16_BPB:
   703 000071D5 B92D000000          <1> 	mov	ecx, 45
   704                              <1> 	
   705                              <1> loc_hd_move_FAT_BPB:
   706 000071DA 89EF                <1> 	mov 	edi, ebp
   707                              <1> 	;mov	esi, ebx ; Boot sector
   708 000071DC 57                  <1> 	push	edi
   709 000071DD 83C706              <1> 	add	edi, LD_BPB
   710 000071E0 F366A5              <1> 	rep	movsw 
   711 000071E3 5E                  <1> 	pop	esi
   712 000071E4 0FB74614            <1> 	movzx	eax, word [esi+LD_BPB+BPB_RsvdSecCnt]
   713 000071E8 03466C              <1> 	add	eax, [esi+LD_StartSector]
   714 000071EB 894660              <1> 	mov	[esi+LD_FATBegin], eax
   715 000071EE 807E0303            <1> 	cmp	byte [esi+LD_FATType], 3
   716 000071F2 7224                <1> 	jb	short loc_set_FAT16_RootDirLoc
   717                              <1> loc_set_FAT32_RootDirLoc:
   718 000071F4 8B462A              <1> 	mov	eax, [esi+LD_BPB+BPB_FATSz32]
   719 000071F7 0FB65E16            <1>         movzx	ebx, byte [esi+LD_BPB+BPB_NumFATs]
   720 000071FB F7E3                <1> 	mul	ebx
   721 000071FD 034660              <1> 	add	eax, [esi+LD_FATBegin]
   722                              <1> loc_set_FAT32_data_begin:
   723 00007200 894668              <1> 	mov	[esi+LD_DATABegin], eax
   724 00007203 894664              <1> 	mov	[esi+LD_ROOTBegin], eax
   725                              <1> 	; If Root Directory Cluster <> 2 then
   726                              <1> 	; change the beginning sector value 
   727                              <1> 	; of the root dir by adding sector offset.
   728 00007206 8B4632              <1> 	mov	eax, [esi+LD_BPB+BPB_RootClus]
   729 00007209 83E802              <1> 	sub	eax, 2
   730 0000720C 7435                <1> 	jz	short short loc_set_32bit_FAT_total_sectors  
   731                              <1> 	;movzx	ebx, byte [esi+LD_BPB+BPB_SecPerClust]
   732 0000720E 8A5E13              <1> 	mov	bl, [esi+LD_BPB+BPB_SecPerClust] 
   733 00007211 F7E3                <1> 	mul	ebx
   734 00007213 014664              <1> 	add	[esi+LD_ROOTBegin], eax
   735 00007216 EB2B                <1> 	jmp	short loc_set_32bit_FAT_total_sectors
   736                              <1> 	;
   737                              <1> loc_set_FAT16_RootDirLoc:
   738 00007218 0FB64616            <1> 	movzx	eax, byte [esi+LD_BPB+BPB_NumFATs]
   739 0000721C 0FB7561C            <1> 	movzx	edx, word [esi+LD_BPB+BPB_FATSz16]
   740 00007220 F7E2                <1> 	mul	edx
   741 00007222 034660              <1> 	add	eax, [esi+LD_FATBegin]  
   742 00007225 894664              <1> 	mov	[esi+LD_ROOTBegin], eax
   743                              <1> loc_set_FAT16_data_begin:
   744 00007228 894668              <1> 	mov	[esi+LD_DATABegin], eax 
   745                              <1> 	;mov	eax, 20h  ; Size of a directory entry
   746                              <1> 	;;movzx	edx, word [esi+LD_BPB+BPB_RootEntCnt]
   747                              <1>         ;mov     dx, [esi+LD_BPB+BPB_RootEntCnt]
   748                              <1>         ;mul	edx
   749                              <1> 	;;mov	ecx, 511
   750                              <1> 	;mov	cx, 511
   751                              <1> 	;add	eax, ecx
   752                              <1> 	;inc	ecx ; 512
   753                              <1> 	;div	ecx
   754                              <1> 	; 14/07/2020
   755 0000722B 0FB74617            <1> 	movzx	eax, word [esi+LD_BPB+BPB_RootEntCnt]
   756 0000722F 6683C00F            <1> 	add	ax, 15
   757 00007233 66C1E804            <1> 	shr	ax, 4 ; / 16 ; (16 entries per sector)
   758 00007237 014668              <1> 	add	[esi+LD_DATABegin], eax
   759                              <1> 	;movzx	eax, word [esi+LD_BPB+BPB_TotalSec16]
   760 0000723A 668B4619            <1> 	mov	ax, [esi+LD_BPB+BPB_TotalSec16]
   761 0000723E 6685C0              <1> 	test	ax, ax
   762                              <1> 	;jz	short loc_set_32bit_FAT_total_sectors
   763                              <1> ;loc_set_16bit_FAT_total_sectors:
   764                              <1> 	;mov	[esi+LD_TotalSectors], eax
   765                              <1> 	;jmp	short loc_set_hd_FAT_cluster_count
   766                              <1> 	; 14/07/2020
   767 00007241 7503                <1> 	jnz	short loc_set_hd_FAT_cluster_count
   768                              <1> loc_set_32bit_FAT_total_sectors:
   769 00007243 8B4626              <1> 	mov	eax, [esi+LD_BPB+BPB_TotalSec32]
   770                              <1> 	;mov	[esi+LD_TotalSectors], eax
   771                              <1> loc_set_hd_FAT_cluster_count:
   772 00007246 894670              <1> 	mov	[esi+LD_TotalSectors], eax ; 14/07/2020
   773 00007249 8B5668              <1> 	mov	edx, [esi+LD_DATABegin]
   774 0000724C 2B566C              <1> 	sub	edx, [esi+LD_StartSector]
   775 0000724F 29D0                <1> 	sub	eax, edx
   776 00007251 31D2                <1> 	xor	edx, edx ; 0
   777 00007253 0FB64E13            <1>         movzx   ecx, byte [esi+LD_BPB+BPB_SecPerClust]
   778 00007257 F7F1                <1>         div	ecx 
   779 00007259 894678              <1> 	mov	[esi+LD_Clusters], eax
   780                              <1> 	; Maximum Valid Cluster Number= EAX +1
   781                              <1> 	; with 2 reserved clusters= EAX +2
   782                              <1> loc_set_hd_FAT_fs_free_sectors:
   783                              <1> 	;mov	dword [esi+LD_FreeSectors], 0
   784 0000725C E855010000          <1> 	call	get_free_FAT_sectors
   785 00007261 720D                <1> 	jc	short loc_validate_hd_FAT_partition_retn
   786 00007263 894674              <1> 	mov	[esi+LD_FreeSectors], eax
   787 00007266 C6467E06            <1> 	mov	byte [esi+LD_MediaChanged], 6  ; Volume Name Reset
   788                              <1> 
   789                              <1> 	; 15/07/2020
   790 0000726A FE05[C6120100]      <1> 	inc 	byte [Last_DOS_DiskNo] ; > 1
   791                              <1> 
   792                              <1> 	;mov	cl, [Last_DOS_DiskNo] 
   793                              <1> 	;add	cl, 'A'
   794                              <1> 	;mov	[esi+LD_FS_Name], cl
   795                              <1> 
   796                              <1> loc_validate_hd_FAT_partition_retn:         
   797 00007270 C3                  <1> 	retn
   798                              <1> 
   799                              <1> validate_hd_fs_partition:
   800                              <1> 	; 03/02/2018
   801                              <1> 	; 09/12/2017
   802                              <1> 	; 13/02/2016
   803                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
   804                              <1> 	; 29/01/2011
   805                              <1> 	; 23/07/2011
   806                              <1> 	; Input
   807                              <1> 	;   DL = Hard/Fixed Disk Drive Number
   808                              <1> 	;   ESI = PartitionTable offset
   809                              <1> 	;   byte [Last_DOS_DiskNo]
   810                              <1> 	; Output
   811                              <1> 	;  cf=0 -> Validated
   812                              <1> 	;   ESI = Logical dos drv desc. table
   813                              <1> 	;   EBX = Singlix FS boot sector buffer
   814                              <1> 	;   byte [Last_DOS_DiskNo]
   815                              <1> 	;  cf=1 -> Not a valid 'Singlix FS' partition
   816                              <1> 	; EAX, EDX, ECX, EDI -> changed 
   817                              <1> 
   818                              <1> 	;mov	esi, PartitionTable
   819 00007271 8A6604              <1> 	mov	ah, [esi+ptFileSystemID]
   820 00007274 80FCA1              <1> 	cmp	ah, 0A1h ; SINGLIX FS1 (trfs1) partition
   821 00007277 7549                <1> 	jne	short loc_validate_hd_fs_partition_stc_retn
   822                              <1> loc_set_valid_hd_fs_partition_params:
   823 00007279 FE05[C6120100]      <1> 	inc	byte [Last_DOS_DiskNo] ; > 1
   824 0000727F 30C0                <1> 	xor	al, al ; mov al, 0
   825                              <1> 	;mov	[drv], dl
   826 00007281 29DB                <1> 	sub	ebx, ebx ; 0
   827 00007283 8A3D[C6120100]      <1> 	mov	bh, [Last_DOS_DiskNo] 
   828 00007289 81C300010900        <1> 	add	ebx, Logical_DOSDisks
   829 0000728F C6430102            <1> 	mov	byte [ebx+LD_DiskType], 2
   830 00007293 885302              <1> 	mov	[ebx+LD_PhyDrvNo], dl
   831                              <1> 	;mov	[ebx+LD_FATType], al ; 0
   832                              <1> 	;mov	[ebx+LD_FSType], ah
   833 00007296 66894303            <1> 	mov	[ebx+LD_FATType], ax
   834                              <1> 	;mov	eax, [esi+ptStartSector]
   835                              <1> 	;mov	[ebx+LD_StartSector], eax
   836                              <1> loc_hd_fs_logical_drv_init:
   837 0000729A 89DD                <1> 	mov	ebp, ebx ; 10/01/2016
   838                              <1> 	;mov	dl, [ebx+LD_PhyDrvNo]
   839 0000729C A0[4A640100]        <1> 	mov	al, [HD_LBA_yes] ; 10/01/2016
   840 000072A1 884305              <1> 	mov	[ebx+LD_LBAYes], al
   841 000072A4 89DE                <1> 	mov	esi, ebx
   842 000072A6 BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff ; buffer address
   843 000072AB 08C0                <1> 	or	al, al
   844 000072AD 7515                <1> 	jnz	short loc_hd_fs_drv_init_load_bs_lba
   845                              <1> loc_hd_fs_drv_init_load_bs_chs:
   846 000072AF 8A7601              <1> 	mov	dh, [esi+ptBeginHead]
   847 000072B2 668B4E02            <1> 	mov	cx, [esi+ptBeginSector]
   848 000072B6 66B80102            <1> 	mov	ax, 0201h ; Read 1 sector
   849                              <1> 	;mov	ebx, DOSBootSectorBuff
   850 000072BA E87CD6FFFF          <1> 	call	int13h
   851 000072BF 7311                <1> 	jnc	short loc_hd_drv_fs_boot_validation
   852                              <1> loc_validate_hd_fs_partition_err_retn:
   853 000072C1 C3                  <1> 	retn
   854                              <1> loc_validate_hd_fs_partition_stc_retn:
   855 000072C2 F9                  <1> 	stc
   856 000072C3 C3                  <1> 	retn
   857                              <1> loc_hd_fs_drv_init_load_bs_lba:
   858                              <1> 	; DL = Physical drive number
   859                              <1> 	;mov	esi, ebx
   860 000072C4 8B4E08              <1>    	mov	ecx, [esi+ptStartSector] ; sector number
   861                              <1> 	;mov	ebx, DOSBootSectorBuff ; buffer address
   862                              <1> 	; LBA read/write (with private LBA function) 
   863                              <1> 	;((Retro UNIX 386 v1 - DISK I/O code by Erdogan Tan))
   864                              <1> 	; dl = physical drive number (0,1, 80h, 81h, 82h, 83h)
   865 000072C7 B41B                <1> 	mov	ah, 1Bh ; LBA read
   866 000072C9 B001                <1> 	mov	al, 1 ; sector count
   867 000072CB E86BD6FFFF          <1> 	call	int13h
   868 000072D0 72EF                <1> 	jc	short loc_validate_hd_fs_partition_err_retn
   869                              <1> loc_hd_drv_fs_boot_validation:
   870                              <1> 	;mov	esi, DOSBootSectorBuff
   871 000072D2 89DE                <1> 	mov	esi, ebx ; Boot sector buffer
   872 000072D4 6681BEFE01000055AA  <1> 	cmp	word [esi+BS_Validation], 0AA55h
   873 000072DD 75E3                <1> 	jne	short loc_validate_hd_fs_partition_stc_retn
   874                              <1>         ;
   875                              <1> 	;Singlix FS Extensions to TR-DOS (7/6/2009) 
   876 000072DF 66817E034653        <1> 	cmp	word [esi+bs_FS_Identifier], 'FS' ; 03/02/2018
   877 000072E5 75DB                <1> 	jne	short loc_validate_hd_fs_partition_stc_retn
   878                              <1>         ;'A1h' check is not necessary
   879                              <1> 	;  if 'FS' check is passed as OK/Yes.
   880 000072E7 807E09A1            <1> 	cmp	byte [esi+bs_FS_PartitionID], 0A1h
   881 000072EB 75D5                <1> 	jne	short loc_validate_hd_fs_partition_stc_retn
   882                              <1> 	;
   883 000072ED 89EF                <1> 	mov	edi, ebp ; 10/01/2016
   884                              <1> 	;
   885 000072EF 8A462D              <1> 	mov	al, byte [esi+bs_FS_LBA_Ready]
   886 000072F2 884705              <1> 	mov	[edi+LD_FS_LBAYes], al
   887                              <1> 	;
   888                              <1> 	; 03/01/2010 CHS -> DOS FAT/BPB compatibility fix
   889 000072F5 8A4608              <1> 	mov	al, [esi+bs_FS_MediaAttrib]
   890 000072F8 884706              <1> 	mov	byte [edi+LD_FS_MediaAttrib], al
   891                              <1> 	;
   892 000072FB 8A460A              <1> 	mov	al, [esi+bs_FS_VersionMaj]
   893 000072FE 884707              <1> 	mov	[edi+LD_FS_VersionMajor], al
   894                              <1> 	;
   895 00007301 668B4606            <1> 	mov	ax, [esi+bs_FS_BytesPerSec]
   896 00007305 66894711            <1> 	mov	[edi+LD_FS_BytesPerSec], ax
   897 00007309 8A462E              <1> 	mov	al, [esi+bs_FS_SecPerTrack]
   898 0000730C 30E4                <1> 	xor	ah, ah ; 09/12/2017
   899 0000730E 6689471E            <1> 	mov	[edi+LD_FS_SecPerTrack], ax
   900 00007312 8A462F              <1> 	mov	al, [esi+bs_FS_Heads]
   901 00007315 66894720            <1> 	mov	[edi+LD_FS_NumHeads], ax
   902                              <1> 	;
   903 00007319 8B4628              <1> 	mov	eax, [esi+bs_FS_UnDelDirD]
   904 0000731C 894722              <1> 	mov	[edi+LD_FS_UnDelDirD], eax
   905 0000731F 8B5618              <1> 	mov	edx, [esi+bs_FS_MATLocation]
   906 00007322 89570C              <1> 	mov	[edi+LD_FS_MATLocation], edx
   907 00007325 8B461C              <1> 	mov	eax, [esi+bs_FS_RootDirD]
   908 00007328 894708              <1> 	mov	[edi+LD_FS_RootDirD], eax
   909 0000732B 8B460C              <1> 	mov	eax, [esi+bs_FS_BeginSector]
   910 0000732E 89476C              <1> 	mov	[edi+LD_FS_BeginSector], eax
   911 00007331 8B4710              <1> 	mov	eax, [edi+bs_FS_VolumeSize]
   912 00007334 894770              <1> 	mov	[edi+LD_FS_VolumeSize], eax
   913                              <1> 	;
   914 00007337 89D0                <1> 	mov	eax, edx ; [edi+LD_FS_MATLocation]
   915 00007339 03476C              <1> 	add	eax, [edi+LD_FS_BeginSector]
   916 0000733C 89FE                <1> 	mov	esi, edi
   917                              <1> mread_hd_fs_MAT_sector:
   918                              <1>        ;mov	ebx, DOSBootSectorBuff
   919 0000733E B901000000          <1> 	mov	ecx, 1
   920 00007343 E8798A0000          <1> 	call	disk_read
   921 00007348 7248                <1> 	jc	short loc_validate_hd_fs_partition_retn
   922                              <1> 	; EDI will not be changed
   923 0000734A 89DE                <1> 	mov	esi, ebx
   924                              <1> use_hdfs_mat_sector_params:
   925 0000734C 8B460C              <1> 	mov	eax, [esi+FS_MAT_DATLocation]
   926 0000734F 894714              <1> 	mov	[edi+LD_FS_DATLocation], eax
   927 00007352 8B4610              <1> 	mov	eax, [esi+FS_MAT_DATScount]
   928 00007355 894718              <1> 	mov	[edi+LD_FS_DATSectors], eax
   929 00007358 8B4614              <1> 	mov	eax, [esi+FS_MAT_FreeSectors]
   930 0000735B 894774              <1>         mov     [edi+LD_FS_FreeSectors], eax
   931 0000735E 8B4618              <1> 	mov	eax, [esi+FS_MAT_FirstFreeSector]
   932 00007361 894778              <1> 	mov	[edi+LD_FS_FirstFreeSector], eax
   933 00007364 8B4708              <1> 	mov	eax, [edi+LD_FS_RootDirD]
   934 00007367 03476C              <1> 	add	eax, [edi+LD_FS_BeginSector]
   935 0000736A 89FE                <1> 	mov	esi, edi   
   936                              <1> read_hd_fs_RDT_sector:
   937 0000736C BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff
   938                              <1> 	;mov	ecx, 1
   939 00007371 B101                <1> 	mov	cl, 1
   940 00007373 E8498A0000          <1> 	call	disk_read
   941 00007378 7218                <1> 	jc	short loc_validate_hd_fs_partition_retn
   942                              <1> 	; EDI will not be changed
   943 0000737A 89DE                <1> 	mov	esi, ebx
   944                              <1> use_hdfs_RDT_sector_params:
   945 0000737C 8B461C              <1> 	mov	eax, [esi+FS_RDT_VolumeSerialNo]
   946 0000737F 894728              <1> 	mov	[edi+LD_FS_VolumeSerial], eax
   947 00007382 57                  <1> 	push	edi
   948                              <1> 	;mov	ecx, 16
   949 00007383 B110                <1> 	mov	cl, 16
   950 00007385 83C640              <1> 	add	esi, FS_RDT_VolumeName
   951 00007388 83C72C              <1> 	add	edi, LD_FS_VolumeName
   952 0000738B F3A5                <1> 	rep	movsd ; 64 bytes
   953 0000738D 5E                  <1> 	pop	esi
   954                              <1> 		; Volume Name Reset
   955 0000738E C6467E06            <1>         mov     byte [esi+LD_FS_MediaChanged], 6
   956                              <1> 	;
   957                              <1>         ;mov	cl, [Last_DOS_DiskNo] 
   958                              <1> 	;add	cl, 'A'
   959                              <1> 	;mov	[esi+LD_FS_Name], cl
   960                              <1> 
   961                              <1> loc_validate_hd_fs_partition_retn:
   962 00007392 C3                  <1> 	retn
   963                              <1> 
   964                              <1> load_masterboot:
   965                              <1> 	; 14/07/2020 (Reset function has been removed)
   966                              <1> 	;
   967                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
   968                              <1> 	; 2005 - 2011
   969                              <1> 	; input -> DL = drive number
   970                              <1> ;	mov	ah, 0Dh ; Alternate disk reset
   971                              <1> ;	call	int13h
   972                              <1> ;	jnc	short pass_reset_error
   973                              <1> ;harddisk_error:
   974                              <1> ;  	retn
   975                              <1> ;pass_reset_error:
   976 00007393 BB[46610100]        <1> 	mov	ebx, MasterBootBuff
   977 00007398 66B80102            <1> 	mov	ax, 0201h
   978 0000739C 66B90100            <1> 	mov	cx, 1
   979 000073A0 30F6                <1> 	xor	dh, dh
   980 000073A2 E894D5FFFF          <1>  	call	int13h
   981 000073A7 720C                <1> 	jc	short harddisk_error
   982                              <1> 	;
   983 000073A9 66813D[44630100]55- <1> 	cmp	word [MBIDCode], 0AA55h
   983 000073B1 AA                  <1>
   984 000073B2 7401                <1> 	je	short load_masterboot_ok
   985 000073B4 F9                  <1> 	stc
   986                              <1> harddisk_error:
   987                              <1> load_masterboot_ok:
   988 000073B5 C3                  <1> 	retn
   989                              <1> 
   990                              <1> get_free_FAT_sectors:
   991                              <1> 	; 21/12/2017
   992                              <1> 	; 29/02/2016
   993                              <1> 	; 13/02/2016
   994                              <1> 	; 04/02/2016
   995                              <1> 	; 07/01/2016 (TRDOS 386 = TRDOS v2.0)
   996                              <1> 	; 11/07/2010
   997                              <1> 	; 21/06/2009
   998                              <1> 	; INPUT: ESI = Logical DOS Drive Description Table address
   999                              <1> 	; OUTPUT: STC => Error
  1000                              <1>         ;	cf = 0 and EAX = Free FAT sectors
  1001                              <1> 	; Also, related parameters and FAT buffer will be reset and updated
  1002                              <1> 
  1003 000073B6 31C0                <1> 	xor	eax, eax
  1004                              <1> 	;mov	[esi+LD_FreeSectors], eax ; Reset
  1005                              <1> 	
  1006 000073B8 807E0302            <1>         cmp     byte [esi+LD_FATType], 2
  1007 000073BC 7654                <1> 	jna	short loc_gfc_get_fat_free_clusters
  1008                              <1> 
  1009                              <1> 	; 29/02/2016
  1010 000073BE 48                  <1> 	dec	eax ; 0FFFFFFFFh
  1011 000073BF 89463A              <1> 	mov	[esi+LD_BPB+BPB_Reserved], eax ; Free cluster count (reset)
  1012 000073C2 89463E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], eax ; First Free Cluster (reset)
  1013 000073C5 40                  <1> 	inc	eax ; 0
  1014                              <1> 	;
  1015 000073C6 668B4636            <1> 	mov	ax, [esi+LD_BPB+BPB_FSInfo]
  1016 000073CA 03466C              <1> 	add	eax, [esi+LD_StartSector]
  1017                              <1> 
  1018 000073CD BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff
  1019 000073D2 B901000000          <1> 	mov	ecx, 1
  1020 000073D7 E8E5890000          <1>  	call	disk_read
  1021 000073DC 7301                <1> 	jnc	short loc_gfc_check_fsinfo_signs
  1022                              <1> retn_gfc_get_fsinfo_sec:
  1023 000073DE C3                  <1> 	retn
  1024                              <1> 
  1025                              <1> loc_gfc_check_fsinfo_signs:
  1026 000073DF BB[56640100]        <1> 	mov 	ebx, DOSBootSectorBuff ; 13/02/2016
  1027 000073E4 813B52526141        <1>         cmp     dword [ebx], 41615252h
  1028 000073EA 7524                <1> 	jne	short retn_gfc_get_fsinfo_stc
  1029                              <1> 	;add	ebx, 484
  1030                              <1> 	;cmp	dword [ebx], 61417272h
  1031 000073EC 81BBE4010000727241- <1> 	cmp	dword [ebx+484], 61417272h
  1031 000073F5 61                  <1>
  1032 000073F6 7518                <1> 	jne	short retn_gfc_get_fsinfo_stc
  1033                              <1> 	;add	ebx, 4
  1034                              <1> 	;mov	eax, [ebx]
  1035 000073F8 8B83E8010000        <1> 	mov	eax, [ebx+488]
  1036                              <1> 	; 29/02/2016
  1037 000073FE 89463A              <1> 	mov	[esi+LD_BPB+BPB_Reserved], eax ; Free cluster count
  1038 00007401 8B93EC010000        <1> 	mov	edx,  [ebx+492] 
  1039 00007407 89463E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], eax ; First Free Cluster
  1040                              <1> 	; 21/12/2017
  1041 0000740A 89C3                <1> 	mov	ebx, eax ; (initial value = 0FFFFFFFFh)
  1042 0000740C 43                  <1> 	inc	ebx ; 0FFFFFFFFh -> 0  
  1043 0000740D 7513                <1> 	jnz	short short retn_from_get_free_fat32_clusters
  1044 0000740F C3                  <1> 	retn
  1045                              <1> 
  1046                              <1> retn_gfc_get_fsinfo_stc:
  1047 00007410 F9                  <1> 	stc
  1048 00007411 C3                  <1> 	retn
  1049                              <1> 
  1050                              <1> loc_gfc_get_fat_free_clusters:
  1051                              <1> 	;mov	eax, 2
  1052 00007412 B002                <1> 	mov	al, 2
  1053                              <1> 	;mov	[FAT_CurrentCluster], eax
  1054                              <1> loc_gfc_loop_get_next_cluster:
  1055 00007414 E8EB4F0000          <1> 	call	get_next_cluster
  1056 00007419 730E                <1> 	jnc	short loc_gfc_free_fat_clusters_cont
  1057 0000741B 21C0                <1> 	and	eax, eax
  1058 0000741D 7411                <1> 	jz	short loc_gfc_pass_inc_free_cluster_count
  1059                              <1>  
  1060                              <1> retn_from_get_free_fat_clusters:
  1061 0000741F 8B4674              <1> 	mov	eax, [esi+LD_FreeSectors] ; Free clusters !
  1062                              <1> retn_from_get_free_fat32_clusters:
  1063 00007422 0FB65E13            <1>         movzx	ebx, byte [esi+LD_BPB+BPB_SecPerClust]
  1064 00007426 F7E3                <1>       	mul	ebx
  1065                              <1> 	;mov	[esi+LD_FreeSectors], eax ; Free sectors
  1066                              <1> retn_get_free_sectors_calc:
  1067 00007428 C3                  <1> 	retn
  1068                              <1> 
  1069                              <1> loc_gfc_free_fat_clusters_cont:
  1070 00007429 09C0                <1> 	or	eax, eax
  1071 0000742B 7503                <1> 	jnz	short loc_gfc_pass_inc_free_cluster_count
  1072 0000742D FF4674              <1> 	inc	dword [esi+LD_FreeSectors] ; Free clusters !
  1073                              <1>    
  1074                              <1> loc_gfc_pass_inc_free_cluster_count:
  1075                              <1> 	;mov	eax, [FAT_CurrentCluster]
  1076 00007430 89C8                <1> 	mov	eax, ecx ; [FAT_CurrentCluster]
  1077 00007432 3B4678              <1> 	cmp	eax, [esi+LD_Clusters]
  1078 00007435 77E8                <1> 	ja	short retn_from_get_free_fat_clusters
  1079 00007437 40                  <1> 	inc	eax
  1080                              <1> 	;mov	[FAT_CurrentCluster], eax
  1081 00007438 EBDA                <1> 	jmp	short loc_gfc_loop_get_next_cluster
  1082                              <1> 
  1083                              <1> floppy_drv_init:
  1084                              <1> 	; 09/12/2017
  1085                              <1> 	; 06/07/2016
  1086                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
  1087                              <1> 	; 24/07/2011
  1088                              <1> 	; 04/07/2009
  1089                              <1> 	; INPUT ->
  1090                              <1> 	;	DL = Drive number (0,1)
  1091                              <1> 	; OUTPUT ->
  1092                              <1> 	;	BL = drive name
  1093                              <1> 	;	BH = drive number
  1094                              <1> 	;	ESI = Logical DOS drv description table
  1095                              <1> 	;	EAX = Volume serial number
  1096                              <1>  
  1097 0000743A BE[AE640000]        <1> 	mov	esi, fd0_type ; 10/01/2016
  1098 0000743F BF00010900          <1> 	mov	edi, Logical_DOSDisks
  1099 00007444 08D2                <1> 	or	dl, dl
  1100 00007446 7407                <1> 	jz	short loc_drv_init_fd0_fd1
  1101 00007448 81C700010000        <1> 	add	edi, 100h
  1102 0000744E 46                  <1> 	inc	esi ; fd1_type ; 10/01/2016
  1103                              <1> loc_drv_init_fd0_fd1:
  1104 0000744F C6477E00            <1> 	mov	byte [edi+LD_MediaChanged], 0
  1105 00007453 803E01              <1> 	cmp	byte [esi], 1 ; type (>0 if it is existing) 
  1106                              <1> 		; 4 = 1.44 MB, 80 track, 3 1/2"
  1107 00007456 7221                <1> 	jb	short read_fd_boot_sector_retn
  1108 00007458 885702              <1> 	mov	[edi+LD_PhyDrvNo], dl
  1109                              <1> read_fd_boot_sector:
  1110 0000745B 30F6                <1> 	xor	dh, dh
  1111 0000745D B904000000          <1> 	mov	ecx, 4 ; Retry Count
  1112                              <1> read_fd_boot_sector_again:
  1113 00007462 51                  <1> 	push 	ecx
  1114                              <1> 	;mov	cx, 1
  1115 00007463 B101                <1> 	mov	cl, 1
  1116 00007465 66B80102            <1> 	mov	ax, 0201h ; Read 1 sector
  1117 00007469 BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff
  1118 0000746E E8C8D4FFFF          <1> 	call	int13h
  1119 00007473 59                  <1> 	pop	ecx
  1120 00007474 7304                <1> 	jnc	short use_fd_boot_sector_params
  1121 00007476 E2EA                <1> 	loop	read_fd_boot_sector_again
  1122                              <1> 
  1123                              <1> read_fd_boot_sector_stc_retn:
  1124 00007478 F9                  <1> 	stc
  1125                              <1> read_fd_boot_sector_retn:
  1126 00007479 C3                  <1> 	retn
  1127                              <1> 
  1128                              <1> use_fd_boot_sector_params:
  1129                              <1> 	;mov	esi, DOSBootSectorBuff
  1130 0000747A 89DE                <1> 	mov	esi, ebx
  1131 0000747C 6681BEFE01000055AA  <1> 	cmp	word [esi+BS_Validation], 0AA55h
  1132 00007485 75F1                <1> 	jne	short read_fd_boot_sector_stc_retn
  1133 00007487 66817E035346        <1>         cmp     word [esi+bs_FS_Identifier], 'SF'
  1134 0000748D 0F85A2000000        <1>         jne     use_fd_fatfs_boot_sector_params
  1135                              <1> 	;
  1136 00007493 8A462D              <1> 	mov	al, [esi+bs_FS_LBA_Ready]
  1137 00007496 884705              <1> 	mov	[edi+LD_FS_LBAYes], al
  1138                              <1> 	;
  1139                              <1> 	; 03/01/2010 CHS -> DOS FAT/BPB compatibility fix
  1140 00007499 8A4608              <1> 	mov	al, [esi+bs_FS_MediaAttrib]
  1141 0000749C 884706              <1> 	mov	[edi+LD_FS_MediaAttrib], al
  1142                              <1> 	;
  1143 0000749F 8A460A              <1>         mov	al, [esi+bs_FS_VersionMaj]
  1144 000074A2 884707              <1> 	mov	byte [edi+LD_FS_VersionMajor], al
  1145 000074A5 668B4606            <1> 	mov	ax, [esi+bs_FS_BytesPerSec]
  1146 000074A9 66894711            <1> 	mov	[edi+LD_FS_BytesPerSec], ax
  1147 000074AD 8A462E              <1> 	mov	al, [esi+bs_FS_SecPerTrack]
  1148 000074B0 28E4                <1> 	sub	ah, ah ; 09/12/2017
  1149 000074B2 6689471E            <1> 	mov	[edi+LD_FS_SecPerTrack], ax
  1150 000074B6 8A462F              <1> 	mov	al, [esi+bs_FS_Heads]
  1151 000074B9 66894720            <1> 	mov	[edi+LD_FS_NumHeads], ax
  1152                              <1> 	;
  1153 000074BD 8B4628              <1> 	mov	eax, [esi+bs_FS_UnDelDirD]
  1154 000074C0 894722              <1> 	mov	[edi+LD_FS_UnDelDirD], eax
  1155 000074C3 8B4618              <1> 	mov	eax, [esi+bs_FS_MATLocation]
  1156 000074C6 89470C              <1> 	mov	[edi+LD_FS_MATLocation], eax
  1157 000074C9 8B461C              <1> 	mov	eax, [esi+bs_FS_RootDirD]
  1158 000074CC 894708              <1> 	mov	[edi+LD_FS_RootDirD], eax
  1159 000074CF 8B460C              <1> 	mov	eax, [esi+bs_FS_BeginSector]
  1160 000074D2 89476C              <1> 	mov	[edi+LD_FS_BeginSector], eax
  1161 000074D5 8B4610              <1> 	mov	eax, [esi+bs_FS_VolumeSize]
  1162 000074D8 894770              <1> 	mov	[edi+LD_FS_VolumeSize], eax
  1163                              <1> 	;		
  1164 000074DB 89FE                <1> 	mov	esi, edi
  1165 000074DD 8B460C              <1>  	mov	eax, [esi+LD_FS_MATLocation]
  1166                              <1> 	;add	eax, [edi+LD_FS_BeginSector]
  1167                              <1> read_fd_MAT_sector_again:
  1168                              <1> 	;mov	ebx, DOSBootSectorBuff
  1169                              <1> 	;mov	ecx, 1
  1170 000074E0 B101                <1> 	mov	cl, 1
  1171 000074E2 E8E0880000          <1> 	call	chs_read
  1172 000074E7 89DE                <1> 	mov	esi, ebx
  1173 000074E9 7301                <1> 	jnc	short use_fdfs_mat_sector_params
  1174                              <1> 	;jmp	short read_fd_boot_sector_retn
  1175 000074EB C3                  <1> 	retn
  1176                              <1> use_fdfs_mat_sector_params:
  1177 000074EC 8B460C              <1> 	mov	eax, [esi+FS_MAT_DATLocation]
  1178 000074EF 894714              <1> 	mov	[edi+LD_FS_DATLocation], eax
  1179 000074F2 8B4610              <1> 	mov	eax, [esi+FS_MAT_DATScount]
  1180 000074F5 894718              <1> 	mov	[edi+LD_FS_DATSectors], eax
  1181 000074F8 8B4714              <1> 	mov	eax, [edi+FS_MAT_FreeSectors]
  1182 000074FB 894774              <1> 	mov	[edi+LD_FS_FreeSectors], eax
  1183 000074FE 8B4618              <1> 	mov	eax, [esi+FS_MAT_FirstFreeSector]
  1184 00007501 894778              <1> 	mov	[edi+LD_FS_FirstFreeSector], eax
  1185                              <1> 	;
  1186 00007504 89FE                <1> 	mov	esi, edi
  1187 00007506 8B4608              <1>  	mov	eax, [esi+LD_FS_RootDirD]
  1188                              <1> read_fd_RDT_sector_again:
  1189                              <1> 	;mov	ebx, DOSBootSectorBuff
  1190                              <1> 	;mov	cx, 1
  1191 00007509 B101                <1> 	mov	cl, 1
  1192 0000750B E8B7880000          <1> 	call	chs_read
  1193 00007510 89DE                <1> 	mov	esi, ebx
  1194 00007512 7220                <1> 	jc	short read_fd_RDT_sector_retn
  1195                              <1> use_fdfs_RDT_sector_params:
  1196 00007514 8B461C              <1> 	mov	eax, [esi+FS_RDT_VolumeSerialNo]
  1197 00007517 894728              <1> 	mov	[edi+LD_FS_VolumeSerial], eax
  1198 0000751A 57                  <1> 	push	edi
  1199                              <1> 	;mov	ecx, 16
  1200 0000751B B110                <1> 	mov	cl, 16	
  1201 0000751D 83C640              <1> 	add	esi, FS_RDT_VolumeName
  1202 00007520 83C72C              <1> 	add	edi, LD_FS_VolumeName
  1203 00007523 F3A5                <1> 	rep	movsd ; 64 bytes
  1204 00007525 5E                  <1> 	pop	esi
  1205 00007526 C6460300            <1> 	mov	byte [esi+LD_FATType], 0
  1206 0000752A C64604A1            <1> 	mov	byte [esi+LD_FSType], 0A1h  
  1207 0000752E E9A5000000          <1>         jmp     loc_cont_use_fd_boot_sector_params
  1208                              <1> 
  1209                              <1> read_fd_RDT_sector_stc_retn:
  1210 00007533 F9                  <1> 	stc
  1211                              <1> read_fd_RDT_sector_retn:
  1212 00007534 C3                  <1> 	retn
  1213                              <1> 
  1214                              <1> use_fd_fatfs_boot_sector_params:
  1215 00007535 807E2629            <1> 	cmp	byte [esi+BS_BootSig], 29h
  1216 00007539 75F8                <1> 	jne	short read_fd_RDT_sector_stc_retn
  1217 0000753B 807E15F0            <1> 	cmp	byte [esi+BPB_Media], 0F0h
  1218 0000753F 72F3                <1> 	jb	short read_fd_RDT_sector_retn
  1219 00007541 57                  <1> 	push	edi
  1220 00007542 83C706              <1> 	add	edi, LD_BPB
  1221                              <1> 	;mov	ecx, 16
  1222 00007545 B110                <1> 	mov	cl, 16
  1223 00007547 F3A5                <1> 	rep	movsd ; 64 bytes 
  1224 00007549 5E                  <1> 	pop	esi
  1225 0000754A 31C0                <1> 	xor	eax, eax
  1226 0000754C 89466C              <1> 	mov	[esi+LD_StartSector], eax ; 0
  1227 0000754F 668B461C            <1> 	mov	ax, [esi+LD_BPB+BPB_FATSz16]
  1228 00007553 8A4E16              <1> 	mov	cl, [esi+LD_BPB+BPB_NumFATs] 
  1229 00007556 F7E1                <1>   	mul	ecx
  1230                              <1> 	; edx = 0 !
  1231 00007558 668B5614            <1> 	mov	dx, [esi+LD_BPB+BPB_RsvdSecCnt]
  1232 0000755C 66895660            <1> 	mov	[esi+LD_FATBegin], dx
  1233                              <1> 	;add	eax, edx
  1234 00007560 6601D0              <1> 	add	ax, dx
  1235 00007563 894664              <1> 	mov	[esi+LD_ROOTBegin], eax
  1236 00007566 894668              <1> 	mov	[esi+LD_DATABegin], eax 
  1237 00007569 668B5617            <1> 	mov	dx, [esi+LD_BPB+BPB_RootEntCnt]
  1238                              <1> 	;;shl	edx, 5 ; * 32 (Size of a directory entry)
  1239                              <1> 	;shl	dx, 5
  1240                              <1> 	;;add	edx, 511
  1241                              <1> 	;add	dx, 511
  1242                              <1> 	;;shr	edx, 9 ; edx = ((edx*32)+511) / 512
  1243                              <1> 	;shr	dx, 9
  1244 0000756D 6683C20F            <1> 	add	dx, 15 ; 06/07/2016 (+(512/32)-1)
  1245 00007571 66C1EA04            <1> 	shr	dx, 4 ; / 16 (==16 entries per sector)
  1246 00007575 015668              <1> 	add 	[esi+LD_DATABegin], edx ; + rd sectors
  1247                              <1> 	;movzx	eax, word [esi+LD_BPB+BPB_TotalSec16]
  1248 00007578 668B4619            <1> 	mov	ax, [esi+LD_BPB+BPB_TotalSec16]
  1249 0000757C 894670              <1> 	mov	[esi+LD_TotalSectors], eax
  1250 0000757F 2B4668              <1> 	sub	eax, [esi+LD_DATABegin]
  1251                              <1>   	;movzx	ecx, byte [esi+LD_BPB+BPB_SecPerClust]
  1252 00007582 8A4E13              <1> 	mov	cl, [esi+LD_BPB+BPB_SecPerClust]  
  1253 00007585 80F901              <1> 	cmp	cl, 1
  1254 00007588 7605                <1> 	jna	short save_fd_fatfs_cluster_count
  1255                              <1> 	;sub	edx, edx
  1256 0000758A 6629D2              <1> 	sub	dx, dx ; 0
  1257                              <1> 	;sub	dl, dl ; 06/07/2016
  1258 0000758D F7F1                <1> 	div	ecx
  1259                              <1> save_fd_fatfs_cluster_count:
  1260 0000758F 894678              <1> 	mov	[esi+LD_Clusters], eax
  1261                              <1> 
  1262                              <1>       ; Maximum Valid Cluster Number = EAX +1
  1263                              <1>       ; with 2 reserved clusters= EAX +2
  1264                              <1>  
  1265                              <1> reset_FAT_buffer_decriptors:
  1266 00007592 29C0                <1> 	sub	eax, eax ; 0  
  1267 00007594 A2[5A660100]        <1> 	mov	[FAT_BuffValidData], al ; 0
  1268 00007599 A2[5B660100]        <1> 	mov	[FAT_BuffDrvName], al ; 0
  1269 0000759E A3[5E660100]        <1> 	mov	[FAT_BuffSector], eax ; 0
  1270                              <1> 
  1271                              <1> read_fd_FAT_sectors:
  1272 000075A3 BB001C0900          <1>   	mov	ebx, FAT_Buffer
  1273 000075A8 668B4614            <1> 	mov	ax, [esi+LD_BPB+BPB_RsvdSecCnt]
  1274                              <1> 	;mov	ecx, 3
  1275 000075AC B103                <1> 	mov	cl, 3 ; 3 sectors
  1276 000075AE E814880000          <1> 	call	chs_read
  1277 000075B3 7240                <1> 	jc	short read_fd_FAT_sectors_retn
  1278                              <1> use_fd_FAT_sectors:
  1279 000075B5 8A4602              <1> 	mov	al, [esi+LD_PhyDrvNo]
  1280 000075B8 0441                <1> 	add	al, 'A' 
  1281 000075BA A2[5B660100]        <1> 	mov	[FAT_BuffDrvName], al 
  1282 000075BF C605[5A660100]01    <1>  	mov	byte [FAT_BuffValidData], 1
  1283 000075C6 E82B000000          <1> 	call	fd_init_calculate_free_clusters
  1284 000075CB 7228                <1> 	jc	short read_fd_FAT_sectors_retn
  1285                              <1>   
  1286                              <1> loc_use_fd_boot_sector_params_FAT:
  1287 000075CD C6460301            <1> 	mov	byte [esi+LD_FATType], 1 ; FAT 12
  1288 000075D1 C6460401            <1> 	mov	byte [esi+LD_FSType], 1
  1289 000075D5 8B462D              <1>         mov     eax, [esi+LD_BPB+VolumeID]
  1290                              <1> loc_cont_use_fd_boot_sector_params:
  1291 000075D8 8A7E02              <1> 	mov	bh, [esi+LD_PhyDrvNo]
  1292 000075DB 887E7D              <1> 	mov	[esi+LD_DParamEntry], bh
  1293 000075DE 88FB                <1> 	mov	bl, bh
  1294 000075E0 80C341              <1> 	add	bl, 'A'
  1295 000075E3 881E                <1> 	mov	byte [esi+LD_Name], bl
  1296 000075E5 C6460101            <1> 	mov	byte [esi+LD_DiskType], 1
  1297 000075E9 C6460500            <1> 	mov	byte [esi+LD_LBAYes], 0
  1298 000075ED C6467C00            <1> 	mov	byte [esi+LD_PartitionEntry], 0
  1299 000075F1 C6467E06            <1> 	mov	byte [esi+LD_MediaChanged], 6 ; Volume Name Reset
  1300                              <1> 
  1301                              <1> read_fd_FAT_sectors_retn:
  1302 000075F5 C3                  <1> 	retn   
  1303                              <1> 
  1304                              <1> fd_init_calculate_free_clusters:
  1305                              <1> 	; 09/12/2017
  1306                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
  1307                              <1> 	; 04/07/2009
  1308                              <1> 	; INPUT ->
  1309                              <1> 	;     ESI = Logical DOS drive description table address
  1310                              <1> 	; OUTPUT ->
  1311                              <1> 	;    [ESI+LD_FreeSectors] will be set
  1312                              <1> 	
  1313 000075F6 29C0                <1> 	sub	eax, eax
  1314 000075F8 894674              <1> 	mov	[esi+LD_FreeSectors], eax ; 0
  1315 000075FB B002                <1> 	mov	al, 2 ; eax = 2
  1316                              <1> 
  1317                              <1> fd_init_loop_get_next_cluster:
  1318 000075FD E830000000          <1> 	call	fd_init_get_next_cluster
  1319 00007602 722D                <1> 	jc	short fd_init_calculate_free_clusters_retn
  1320                              <1> 
  1321                              <1> fd_init_free_fat_clusters:
  1322                              <1> 	;cmp 	eax, 0
  1323                              <1> 	;ja	short fd_init_pass_inc_free_cluster_count
  1324                              <1> 	;and	eax, eax
  1325                              <1> 	;jnz	short fd_init_pass_inc_free_cluster_count
  1326 00007604 6621C0              <1> 	and	ax, ax
  1327 00007607 7504                <1> 	jnz	short fd_init_pass_inc_free_cluster_count
  1328                              <1> 	;inc	dword [esi+LD_FreeSectors]
  1329 00007609 66FF4674            <1>         inc	word [esi+LD_FreeSectors]
  1330                              <1>     
  1331                              <1> fd_init_pass_inc_free_cluster_count:
  1332                              <1>   	;mov	eax, [FAT_CurrentCluster]
  1333 0000760D 66A1[56660100]      <1> 	mov	ax, [FAT_CurrentCluster]
  1334                              <1> 	;cmp	eax, [esi+LD_Clusters]
  1335 00007613 663B4678            <1> 	cmp	ax, [esi+LD_Clusters]
  1336 00007617 7704                <1> 	ja	short short retn_from_fd_init_calculate_free_clusters
  1337                              <1> 	;inc	eax
  1338 00007619 6640                <1> 	inc	ax
  1339 0000761B EBE0                <1> 	jmp	short fd_init_loop_get_next_cluster
  1340                              <1> 
  1341                              <1> retn_from_fd_init_calculate_free_clusters:
  1342 0000761D 8A4613              <1>   	mov	al, [esi+LD_BPB+BPB_SecPerClust]
  1343 00007620 3C01                <1>   	cmp	al, 1
  1344 00007622 760D                <1> 	jna	short fd_init_calculate_free_clusters_retn
  1345                              <1> 	;movzx	eax, al
  1346 00007624 30E4                <1> 	xor	ah, ah ; 09/12/2017
  1347                              <1> 	;mov	ecx, [esi+LD_FreeSectors]
  1348 00007626 668B4E74            <1> 	mov	cx, [esi+LD_FreeSectors] ; Count of free clusters
  1349                              <1>   	;mul	ecx
  1350 0000762A 66F7E1              <1> 	mul	cx
  1351                              <1> 	;mov	[esi+LD_FreeSectors], eax
  1352 0000762D 66894674            <1> 	mov	[esi+LD_FreeSectors], ax
  1353                              <1> fd_init_calculate_free_clusters_retn:
  1354 00007631 C3                  <1> 	retn
  1355                              <1> 
  1356                              <1> fd_init_get_next_cluster:
  1357                              <1> 	; 04/02/2016
  1358                              <1> 	; 02/02/2016
  1359                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
  1360                              <1> 	; 04/07/2009
  1361                              <1> 	; INPUT ->
  1362                              <1> 	;    EAX = Current cluster
  1363                              <1> 	;    ESI = Logical DOS drive description table address
  1364                              <1> 	;    EDX = 0
  1365                              <1> 	; OUTPUT ->
  1366                              <1> 	;    EAX = Next cluster
  1367                              <1> 
  1368 00007632 A3[56660100]        <1> 	mov	[FAT_CurrentCluster], eax
  1369                              <1> fd_init_get_next_cluster_readnext:
  1370 00007637 29D2                <1> 	sub	edx, edx ; 0
  1371 00007639 BB00040000          <1>   	mov	ebx, 1024 ; 400h
  1372 0000763E F7F3                <1>   	div	ebx
  1373                              <1>   	; EAX = Count of 3 FAT sectors
  1374                              <1>   	; EDX = Buffer entry index
  1375 00007640 89C1                <1> 	mov	ecx, eax
  1376                              <1> 	;mov	eax, 3
  1377 00007642 B003                <1> 	mov	al, 3
  1378 00007644 F7E2                <1> 	mul	edx ; Multiply by 3
  1379 00007646 66D1E8              <1> 	shr	ax, 1 ; Divide by 2
  1380 00007649 89C3                <1> 	mov	ebx, eax ; Buffer byte offset
  1381 0000764B 81C3001C0900        <1> 	add	ebx, FAT_Buffer
  1382 00007651 89C8                <1> 	mov	eax, ecx
  1383                              <1> 	;mov	edx, 3
  1384 00007653 66BA0300            <1> 	mov	dx, 3
  1385 00007657 F7E2                <1> 	mul	edx 
  1386                              <1>   	; EAX = FAT Beginning Sector
  1387                              <1> 	; EDX = 0
  1388 00007659 8A0E                <1> 	mov	cl, [esi+LD_Name]
  1389                              <1> 	;cmp	byte [FAT_BuffValidData], 0
  1390                              <1> 	;jna	short fd_init_load_FAT_sectors0
  1391 0000765B 3A0D[5B660100]      <1> 	cmp	cl, [FAT_BuffDrvName]
  1392 00007661 751E                <1> 	jne	short fd_init_load_FAT_sectors0
  1393 00007663 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
  1394 00007669 751C                <1> 	jne	short fd_init_load_FAT_sectors1
  1395                              <1> 	;mov	eax, [FAT_CurrentCluster]
  1396 0000766B A0[56660100]        <1> 	mov	al, [FAT_CurrentCluster]
  1397                              <1> 	;shr	eax, 1
  1398 00007670 D0E8                <1> 	shr	al, 1
  1399 00007672 668B03              <1> 	mov	ax, [ebx]
  1400 00007675 7306                <1>   	jnc	short fd_init_gnc_even
  1401 00007677 66C1E804            <1> 	shr	ax, 4
  1402                              <1> fd_init_gnc_clc_retn:
  1403 0000767B F8                  <1> 	clc
  1404 0000767C C3                  <1> 	retn
  1405                              <1> 
  1406                              <1> fd_init_gnc_even:
  1407 0000767D 80E40F              <1> 	and	ah, 0Fh
  1408 00007680 C3                  <1> 	retn
  1409                              <1> 
  1410                              <1> fd_init_load_FAT_sectors0:
  1411 00007681 880D[5B660100]      <1> 	mov 	[FAT_BuffDrvName], cl
  1412                              <1> fd_init_load_FAT_sectors1:
  1413 00007687 C605[5A660100]00    <1> 	mov	byte [FAT_BuffValidData], 0
  1414 0000768E A3[5E660100]        <1> 	mov	[FAT_BuffSector], eax
  1415 00007693 034660              <1> 	add	eax, [esi+LD_FATBegin]
  1416 00007696 BB001C0900          <1>  	mov	ebx, FAT_Buffer
  1417                              <1> 	;movzx	ecx, word [esi+LD_BPB+BPB_FATSz16]
  1418 0000769B 668B4E1C            <1> 	mov	cx, [esi+LD_BPB+BPB_FATSz16]
  1419 0000769F 662B0D[5E660100]    <1> 	sub	cx, [FAT_BuffSector]
  1420                              <1>         ;cmp	ecx, 3
  1421 000076A6 6683F903            <1> 	cmp	cx, 3
  1422 000076AA 7605                <1> 	jna	short fdinit_pass_fix_sector_count_3
  1423                              <1> 	;mov	ecx, 3
  1424 000076AC B903000000          <1> 	mov	ecx, 3
  1425                              <1> fdinit_pass_fix_sector_count_3:  
  1426 000076B1 E811870000          <1> 	call	chs_read
  1427 000076B6 730D                <1> 	jnc	short fd_init_FAT_sectors_no_load_error
  1428 000076B8 C605[5A660100]00    <1> 	mov	byte [FAT_BuffValidData], 0
  1429                              <1> 		; Drv not ready or read Error !
  1430 000076BF B80F000000          <1> 	mov	eax, ERR_DRV_NOT_RDY ; 15
  1431                              <1> 	;xor	edx, edx
  1432 000076C4 C3                  <1> 	retn
  1433                              <1> 
  1434                              <1> fd_init_FAT_sectors_no_load_error:
  1435 000076C5 C605[5A660100]01    <1> 	mov	byte [FAT_BuffValidData], 1
  1436 000076CC A1[56660100]        <1> 	mov	eax, [FAT_CurrentCluster]
  1437 000076D1 E961FFFFFF          <1>         jmp     fd_init_get_next_cluster_readnext
  1438                              <1> 
  1439                              <1> get_FAT_volume_name:
  1440                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
  1441                              <1> 	; 12/09/2009
  1442                              <1> 	; INPUT ->
  1443                              <1> 	;	BH = Logical DOS drive number (0,1,2,3,4 ...)
  1444                              <1> 	;       BL = 0
  1445                              <1> 	; OUTPUT ->
  1446                              <1> 	;	CF = 0 -> ESI = Volume name address
  1447                              <1> 	; 	CF = 1 -> Root volume name not found
  1448                              <1> 
  1449                              <1> 	;mov 	ah, 0FFh
  1450                              <1> 	;mov 	al, [Last_Dos_DiskNo]
  1451                              <1> 	;cmp 	al, bh
  1452                              <1> 	;jb     short loc_gfvn_dir_load_err
  1453                              <1> 
  1454 000076D6 89DE                <1> 	mov	esi, ebx
  1455 000076D8 81E600FF0000        <1> 	and	esi, 0FF00h ; esi = bh
  1456 000076DE 81C600010900        <1> 	add	esi, Logical_DOSDisks
  1457 000076E4 8A06                <1> 	mov     al, [esi+LD_Name]
  1458 000076E6 8A6603              <1> 	mov     ah, [esi+LD_FATType]
  1459 000076E9 80FC01              <1> 	cmp     ah, 1
  1460 000076EC 7210                <1> 	jb    	short loc_gfvn_dir_load_err
  1461 000076EE 3C41                <1> 	cmp 	al, 'A'
  1462 000076F0 720C                <1> 	jb      short loc_gfvn_dir_load_err
  1463 000076F2 80FC02              <1> 	cmp 	ah, 2 
  1464 000076F5 7708                <1> 	ja      short get_FAT32_root_cluster
  1465                              <1> 	
  1466 000076F7 E8634E0000          <1> 	call    load_FAT_root_directory
  1467 000076FC 730B                <1> 	jnc     short loc_get_volume_name
  1468                              <1> 
  1469                              <1> loc_gfvn_dir_load_err:
  1470 000076FE C3                  <1> 	retn
  1471                              <1> 
  1472                              <1> get_FAT32_root_cluster:
  1473 000076FF 8B4632              <1> 	mov	eax, [esi+LD_BPB+BPB_RootClus]
  1474 00007702 E8E34E0000          <1> 	call    load_FAT_sub_directory
  1475 00007707 7224                <1> 	jc	short loc_get_volume_name_retn
  1476                              <1> 
  1477                              <1> loc_get_volume_name:
  1478 00007709 BE00000800          <1>         mov     esi, Directory_Buffer
  1479 0000770E 6631C9              <1> 	xor	cx, cx ; 0
  1480                              <1> check_root_volume_name:
  1481 00007711 8A06                <1> 	mov	al, [esi]
  1482 00007713 08C0                <1> 	or      al, al
  1483 00007715 7416                <1> 	jz      short loc_get_volume_name_retn
  1484 00007717 807E0B08            <1> 	cmp     byte [esi+0Bh], 08h
  1485 0000771B 7410                <1> 	je      short loc_get_volume_name_retn
  1486 0000771D 663B0D[6F660100]    <1> 	cmp     cx, [DirBuff_LastEntry]
  1487 00007724 7308                <1> 	jnb     short pass_check_root_volume_name
  1488 00007726 6641                <1> 	inc     cx
  1489 00007728 83C620              <1> 	add     esi, 32
  1490 0000772B EBE4                <1> 	jmp     short check_root_volume_name
  1491                              <1> 
  1492                              <1> loc_get_volume_name_retn:
  1493 0000772D C3                  <1> 	retn
  1494                              <1>     
  1495                              <1> pass_check_root_volume_name:
  1496 0000772E 803D[6B660100]03    <1> 	cmp	byte [DirBuff_FATType], 3
  1497 00007735 7230                <1> 	jb	short loc_get_volume_name_retn_xor
  1498                              <1> 
  1499 00007737 BB001C0900          <1> 	mov	ebx, FAT_Buffer
  1500 0000773C BE00010900          <1> 	mov	esi, Logical_DOSDisks
  1501 00007741 31C0                <1> 	xor	eax, eax
  1502 00007743 8A25[6A660100]      <1> 	mov	ah, [DirBuff_DRV]
  1503 00007749 80EC41              <1> 	sub	ah, 'A' 
  1504 0000774C 01C6                <1> 	add	esi, eax
  1505 0000774E A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
  1506 00007753 E8AC4C0000          <1> 	call	get_next_cluster
  1507 00007758 7305                <1> 	jnc 	short loc_gfvn_load_FAT32_dir_cluster
  1508                              <1>   	
  1509 0000775A 83F801              <1> 	cmp     eax, 1
  1510 0000775D F5                  <1> 	cmc
  1511 0000775E C3                  <1> 	retn
  1512                              <1>   
  1513                              <1> loc_gfvn_load_FAT32_dir_cluster:
  1514 0000775F E8864E0000          <1> 	call	load_FAT_sub_directory
  1515 00007764 73A3                <1> 	jnc	short loc_get_volume_name
  1516 00007766 C3                  <1> 	retn
  1517                              <1> 
  1518                              <1> loc_get_volume_name_retn_xor:
  1519 00007767 31C0                <1> 	xor 	eax, eax
  1520 00007769 C3                  <1> 	retn
  1521                              <1> 
  1522                              <1> get_media_change_status:
  1523                              <1> 	; 10/01/2016 (TRDOS 386 = TRDOS v2.0)
  1524                              <1> 	; 09/09/2009
  1525                              <1> 	; INPUT:
  1526                              <1> 	;     DL = Drive number (physical)
  1527                              <1> 	; OUTPUT: clc & AH = 6 media changed
  1528                              <1> 	;     clc & AH = 0 media not changed         
  1529                              <1> 	;     stc -> Drive not ready or an error 
  1530                              <1>   
  1531 0000776A B416                <1> 	mov	ah, 16h
  1532 0000776C E8CAD1FFFF          <1>   	call	int13h
  1533 00007771 80FC06              <1> 	cmp	ah, 06h
  1534 00007774 7405                <1> 	je	short loc_gmc_status_retn
  1535 00007776 08E4                <1> 	or	ah, ah
  1536 00007778 7401                <1> 	jz	short loc_gmc_status_retn
  1537                              <1> loc_gmc_status_stc_retn:    
  1538 0000777A F9                  <1> 	stc
  1539                              <1> loc_gmc_status_retn:
  1540 0000777B C3                  <1> 	retn
  2863                                  %include 'trdosk3.s' ; 06/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - MAIN PROGRAM : trdosk3.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 31/12/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 06/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; MAINPROG.ASM (09/11/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; MAINPROG.ASM [ TRDOS KERNEL - COMMAND EXECUTER SECTION - MAIN PROGRAM ]
    14                              <1> ; (c) 2004-2011  Erdogan TAN  [ 17/01/2004 ]  Last Update: 09/11/2011
    15                              <1> ; CMD_INTR.ASM [ TRDOS Command Interpreter Procedure ] Last Update: 09/11/2011
    16                              <1> ; DIR.ASM [ DIRECTORY FUNCTIONS ] Last Update: 09/10/2011
    17                              <1> ; FILE.ASM [ FILE FUNCTIONS ] Last Update: 09/10/2011
    18                              <1> 
    19                              <1> change_current_drive:
    20                              <1> 	; 16/10/2016
    21                              <1> 	; 02/02/2016
    22                              <1> 	; 15/01/2016 (TRDOS 386 = TRDOS v2.0)
    23                              <1> 	; 18/08/2011
    24                              <1> 	; 09/09/2009
    25                              <1> 	; INPUT:
    26                              <1> 	;   DL = Logical DOS Drive Number
    27                              <1> 	; OUTPUT:
    28                              <1> 	;  cf=1 -> Not successful
    29                              <1> 	;   EAX = Error code
    30                              <1> 	;  cf=0 ->
    31                              <1> 	;   EAX = 0 (successful)
    32                              <1> 
    33 0000777C 31DB                <1> 	xor	ebx, ebx
    34 0000777E 88D7                <1> 	mov	bh, dl
    35                              <1> 
    36                              <1> 	;cmp	dl, 1
    37                              <1> 	;jna	short loc_ccdrv_initial_media_change_check
    38                              <1> 	;cmp	bh, [Last_Dos_DiskNo]
    39                              <1> 	;ja	short loc_ccdrv_drive_not_ready_err
    40                              <1> 
    41                              <1> loc_ccdrv_initial_media_change_check:
    42 00007780 BE00010900          <1> 	mov	esi, Logical_DOSDisks
    43 00007785 01DE                <1> 	add	esi, ebx
    44                              <1> loc_ccdrv_dos_drive_name_check:
    45 00007787 80FA02              <1> 	cmp	dl, 2
    46 0000778A 720F                <1> 	jb	short loc_ccdrv_dos_drive_name_check_ok
    47                              <1> 
    48 0000778C 8A06                <1> 	mov	al, [esi+LD_Name]
    49 0000778E 2C41                <1> 	sub	al, 'A'
    50 00007790 38D0                <1> 	cmp	al, dl
    51 00007792 7407                <1> 	je	short loc_ccdrv_dos_drive_name_check_ok
    52                              <1> 
    53                              <1> loc_ccdrv_drive_not_ready_err:
    54                              <1> 	; 16/10/2016 (15h -> 15)
    55 00007794 B80F000000          <1> 	mov	eax, 15 ; Drive not ready
    56                              <1> loc_change_current_drive_stc_retn:
    57 00007799 F9                  <1> 	stc
    58 0000779A C3                  <1> 	retn  
    59                              <1> 
    60                              <1> loc_ccdrv_dos_drive_name_check_ok:
    61 0000779B 8A667E              <1> 	mov	ah, [esi+LD_MediaChanged]
    62 0000779E 80FC06              <1> 	cmp	ah, 6  ; VOLUME NAME CHECK/MOVE SIGN
    63 000077A1 7455                <1> 	je	short loc_ccdrv_get_FAT_volume_name_0
    64                              <1> 
    65 000077A3 80FA01              <1> 	cmp	dl, 1
    66 000077A6 777D                <1> 	ja	short loc_gmcs_init_drv_hd
    67                              <1> 
    68                              <1> loc_gmcs_init_drv_fd:
    69 000077A8 08E4                <1> 	or	ah, ah 
    70                              <1> 	; AH = 1 is initialization sign (invalid_fd_parameter)
    71 000077AA 7517                <1> 	jnz	short loc_ccdrv_call_fd_init
    72                              <1> 
    73 000077AC E8B9FFFFFF          <1> 	call	get_media_change_status
    74 000077B1 72E1                <1> 	jc	short loc_ccdrv_drive_not_ready_err
    75                              <1> 
    76 000077B3 20E4                <1> 	and	ah, ah
    77 000077B5 7476                <1> 	jz	short loc_change_current_drv3
    78                              <1> 
    79 000077B7 80F406              <1> 	xor	ah, 6
    80 000077BA 75D8                <1> 	jnz	short loc_ccdrv_drive_not_ready_err
    81                              <1> 
    82                              <1> loc_ccdrv_call_fd_init_check_vol_id:
    83 000077BC E8440A0000          <1> 	call	get_volume_serial_number
    84 000077C1 730D                <1> 	jnc	short loc_ccdrv_check_vol_serial
    85                              <1> 
    86                              <1> loc_ccdrv_call_fd_init:
    87 000077C3 E872FCFFFF          <1> 	call	floppy_drv_init
    88 000077C8 731A                <1> 	jnc	short loc_reset_drv_fd_current_dir
    89                              <1> 
    90                              <1> loc_ccdrv_fdinit_fail_retn:
    91                              <1> 	; 16/10/2016
    92 000077CA B80F000000          <1> 	mov	eax, 15 ; Drive not ready
    93 000077CF C3                  <1> 	retn
    94                              <1> 
    95                              <1> loc_ccdrv_check_vol_serial:
    96 000077D0 A3[3C5F0100]        <1> 	mov	[Current_VolSerial], eax
    97                              <1> 	;mov	dl, bh
    98 000077D5 E860FCFFFF          <1> 	call	floppy_drv_init
    99 000077DA 72EE                <1> 	jc	short loc_ccdrv_fdinit_fail_retn
   100                              <1> 
   101 000077DC 3B05[3C5F0100]      <1> 	cmp	eax, [Current_VolSerial]
   102 000077E2 7445                <1> 	je	short loc_change_current_drv2
   103                              <1> 
   104                              <1> loc_reset_drv_fd_current_dir:
   105 000077E4 31C0                <1> 	xor	eax, eax              
   106 000077E6 88467F              <1>         mov	[esi+LD_CDirLevel], al
   107 000077E9 89F7                <1> 	mov	edi, esi
   108 000077EB 81C780000000        <1> 	add	edi, LD_CurrentDirectory
   109 000077F1 B920000000          <1> 	mov	ecx, 32
   110 000077F6 F3AB                <1> 	rep	stosd   
   111                              <1>  
   112                              <1> loc_ccdrv_get_FAT_volume_name_0:
   113 000077F8 8A4603              <1> 	mov	al, [esi+LD_FATType]
   114 000077FB 08C0                <1> 	or	al, al
   115 000077FD 742A                <1> 	jz	short loc_change_current_drv2
   116                              <1> 
   117 000077FF 56                  <1> 	push	esi 
   118 00007800 3C02                <1> 	cmp	al, 2
   119 00007802 7705                <1> 	ja	short loc_ccdrv_get_FAT32_vol_name
   120                              <1>              
   121                              <1> loc_ccdrv_get_FAT2_16_vol_name:
   122 00007804 83C631              <1> 	add	esi, LD_BPB + VolumeLabel
   123 00007807 EB03                <1> 	jmp	short loc_ccdrv_get_FAT_volume_name_1
   124                              <1> 
   125                              <1> loc_ccdrv_get_FAT32_vol_name:
   126 00007809 83C64D              <1> 	add	esi, LD_BPB + FAT32_VolLab
   127                              <1> loc_ccdrv_get_FAT_volume_name_1:
   128 0000780C 53                  <1> 	push	ebx
   129 0000780D 56                  <1> 	push	esi
   130 0000780E E8C3FEFFFF          <1> 	call	get_FAT_volume_name
   131 00007813 5F                  <1> 	pop	edi
   132 00007814 5B                  <1> 	pop	ebx
   133                              <1> 	; BL = 0
   134 00007815 720B                <1> 	jc	short loc_change_current_drv1
   135 00007817 20C0                <1> 	and	al, al
   136 00007819 7407                <1> 	jz	short loc_change_current_drv1
   137                              <1> 
   138                              <1> loc_ccdrv_move_FAT_volume_name:
   139 0000781B B90B000000          <1> 	mov	ecx, 11
   140 00007820 F3A4                <1> 	rep	movsb
   141                              <1> 
   142                              <1> loc_change_current_drv1:
   143 00007822 5E                  <1> 	pop	esi
   144 00007823 EB04                <1> 	jmp	short loc_change_current_drv2
   145                              <1> 
   146                              <1> loc_gmcs_init_drv_hd:
   147 00007825 08E4                <1> 	or	ah, ah
   148 00007827 7404                <1> 	jz	short loc_change_current_drv3
   149                              <1> 	; BL = 0, BH = Logical DOS drive number
   150                              <1> loc_change_current_drv2:
   151 00007829 C6467E00            <1> 	mov	byte [esi+LD_MediaChanged], 0
   152                              <1> loc_change_current_drv3:
   153 0000782D 883D[465F0100]      <1> 	mov	[Current_Drv], bh
   154                              <1> 
   155                              <1> 	;call	restore_current_directory
   156                              <1> 	;retn
   157                              <1> 
   158                              <1> restore_current_directory:
   159                              <1> 	; 11/02/2016
   160                              <1> 	; 15/01/2016 (TRDOS 386 = TRDOS v2.0)
   161                              <1> 	; 25/01/2010
   162                              <1> 	; 12/10/2009
   163                              <1> 	;
   164                              <1> 	; INPUT:
   165                              <1> 	;   ESI = Logical DOS Drive Description Table
   166                              <1> 	;
   167                              <1> 	; OUTPUT:
   168                              <1> 	;   ESI = Logical DOS Drive Description Table
   169                              <1> 	;   EDI = offset Current_Dir_Drv 
   170                              <1> 
   171 00007833 8A4603              <1> 	mov	al, [esi+LD_FATType]
   172 00007836 A2[455F0100]        <1> 	mov	[Current_FATType], al
   173                              <1> 
   174 0000783B 8A26                <1> 	mov	ah, [esi+LD_Name] 
   175 0000783D 8825[475F0100]      <1> 	mov	[Current_Dir_Drv], ah
   176                              <1> 
   177 00007843 20C0                <1> 	and	al, al
   178 00007845 741D                <1> 	jz	short loc_restore_FS_current_directory
   179                              <1> 
   180                              <1> loc_restore_FAT_current_directory:
   181 00007847 8A667F              <1> 	mov	ah, [esi+LD_CDirLevel]
   182 0000784A 8825[445F0100]      <1> 	mov	[Current_Dir_Level], ah
   183 00007850 08E4                <1> 	or	ah, ah
   184 00007852 7416                <1>         jz	short loc_ccdrv_reset_cdir_FAT_12_16_32_fcluster
   185                              <1> 
   186 00007854 0FB6D4              <1> 	movzx	edx, ah
   187 00007857 C0E204              <1> 	shl	dl, 4 ; * 16
   188 0000785A 01F2                <1>         add	edx, esi
   189 0000785C 8B828C000000        <1> 	mov	eax, [edx+LD_CurrentDirectory+12]
   190 00007862 EB2C                <1> 	jmp	short loc_ccdrv_reset_cdir_FAT_fcluster
   191                              <1> 
   192                              <1> loc_restore_FS_current_directory:
   193 00007864 E8BC4D0000          <1> 	call	load_current_FS_directory 
   194 00007869 C3                  <1> 	retn 
   195                              <1> 
   196                              <1> loc_ccdrv_reset_cdir_FAT_12_16_32_fcluster:
   197 0000786A 3C03                <1> 	cmp	al, 3
   198 0000786C 7205                <1> 	jb	short loc_ccdrv_reset_cdir_FAT_12_16_fcluster
   199                              <1> loc_ccdrv_reset_cdir_FAT32_fcluster:
   200 0000786E 8B4632              <1> 	mov	eax, [esi+LD_BPB+FAT32_RootFClust]
   201 00007871 EB04                <1> 	jmp	short loc_ccdrv_check_rootdir_sign
   202                              <1> loc_ccdrv_reset_cdir_FAT_12_16_fcluster:   
   203 00007873 30C0                <1> 	xor	al, al  ; xor eax, eax
   204 00007875 31D2                <1> 	xor	edx, edx
   205                              <1> loc_ccdrv_check_rootdir_sign:
   206 00007877 80BE8000000000      <1> 	cmp	byte [esi+LD_CurrentDirectory], 0
   207 0000787E 7510                <1> 	jne	short loc_ccdrv_reset_cdir_FAT_fcluster
   208                              <1> loc_ccdrv_set_rootdir_FAT_fcluster:
   209 00007880 89868C000000        <1>         mov     [esi+LD_CurrentDirectory+12], eax
   210 00007886 C78680000000524F4F- <1> 	mov	dword [esi+LD_CurrentDirectory], 'ROOT'
   210 0000788F 54                  <1>
   211                              <1> 
   212                              <1> loc_ccdrv_reset_cdir_FAT_fcluster:
   213 00007890 A3[405F0100]        <1> 	mov	[Current_Dir_FCluster], eax
   214                              <1> 
   215 00007895 BF[A3660100]        <1> 	mov	edi, PATH_Array
   216 0000789A 89F2                <1> 	mov	edx, esi
   217 0000789C 81C680000000        <1> 	add	esi, LD_CurrentDirectory
   218 000078A2 B920000000          <1> 	mov	ecx, 32
   219 000078A7 F3A5                <1> 	rep	movsd
   220                              <1> 
   221 000078A9 E84C2D0000          <1> 	call	change_prompt_dir_string
   222                              <1> 	
   223 000078AE 89D6                <1> 	mov	esi, edx
   224                              <1> 	
   225 000078B0 29C0                <1>         sub	eax, eax
   226                              <1>        ;sub	edx, edx
   227 000078B2 BF[475F0100]        <1> 	mov	edi, Current_Dir_Drv
   228                              <1> 
   229 000078B7 A2[C7120100]        <1> 	mov	[Restore_CDIR], al ; 0
   230 000078BC C3                  <1> 	retn
   231                              <1> 
   232                              <1> dos_prompt:
   233                              <1> 	; 06/05/2016
   234                              <1> 	; 30/01/2016
   235                              <1> 	; 29/01/2016
   236                              <1> 	; 16/01/2016 (TRDOS 386 = TRDOS v2.0)
   237                              <1> 	; 15/09/2011
   238                              <1> 	; 13/09/2009
   239                              <1> 	; 2004-2005
   240                              <1> 
   241                              <1> 	; 06/05/2016
   242 000078BD C705[006B0100]-     <1> 	mov	dword [mainprog_return_addr], return_from_cmd_interpreter
   242 000078C3 [71790000]          <1>
   243                              <1> 
   244                              <1> loc_TRDOS_prompt:
   245 000078C7 BF[46600100]        <1> 	mov	edi, TextBuffer
   246 000078CC C6075B              <1> 	mov	byte [edi], "["
   247 000078CF 47                  <1> 	inc	edi
   248 000078D0 BE[1A130100]        <1> 	mov	esi, TRDOSPromptLabel
   249                              <1> get_next_prompt_label_char:
   250 000078D5 803E20              <1> 	cmp	byte [esi], 20h
   251 000078D8 7203                <1> 	jb	short pass_prompt_label
   252 000078DA A4                  <1> 	movsb
   253 000078DB EBF8                <1> 	jmp	short get_next_prompt_label_char
   254                              <1> pass_prompt_label:
   255 000078DD C6075D              <1> 	mov	byte [edi], "]"
   256 000078E0 47                  <1> 	inc	edi
   257 000078E1 C60720              <1> 	mov	byte [edi], 20h
   258 000078E4 47                  <1> 	inc	edi
   259 000078E5 BE[475F0100]        <1> 	mov	esi, Current_Dir_Drv
   260 000078EA 66A5                <1> 	movsw
   261 000078EC A4                  <1> 	movsb 
   262                              <1> loc_prompt_current_directory:
   263 000078ED 803E20              <1> 	cmp	byte [esi], 20h
   264 000078F0 7203                <1> 	jb	short pass_prompt_current_directory
   265 000078F2 A4                  <1> 	movsb
   266 000078F3 EBF8                <1> 	jmp	short loc_prompt_current_directory  
   267                              <1> pass_prompt_current_directory:
   268 000078F5 C6073E              <1> 	mov	byte [edi], '>'
   269 000078F8 47                  <1> 	inc	edi
   270 000078F9 C60700              <1> 	mov	byte [edi], 0  
   271 000078FC BE[46600100]        <1> 	mov	esi, TextBuffer
   272 00007901 E8FFF2FFFF          <1> 	call	print_msg
   273                              <1>         
   274                              <1> 	;sub	bh, bh ; video page = 0
   275                              <1> 	;call	get_cpos ; get cursor position
   276 00007906 668B15[9E5E0100]    <1> 	mov	dx, [CURSOR_POSN] ; video page 0
   277 0000790D 8815[A65F0100]      <1> 	mov	[CursorColumn], dl
   278                              <1> 
   279                              <1> 	; 30/01/2016 (to show cursor on the row, again)
   280                              <1> 	; (Initial color attributes of video page 0 is 0)
   281                              <1> 	; (see: 'StartPMP' in trdos386.s)
   282                              <1> 	; 
   283                              <1> 	;mov	edi, 0B8000h ; start of video page 0
   284                              <1> 	;movzx	ecx, dl ; column	 
   285                              <1> 	;mov	al, 80
   286                              <1> 	;mul	dh
   287                              <1> 	;add	ax, cx
   288                              <1> 	;shl	ax, 1 ; character + attribute
   289                              <1> 	;add	di, ax ; (2*80*row) + (2*column)
   290                              <1> 	;neg	cl
   291                              <1> 	;add	cl, 80
   292                              <1> 	;mov	ax, 700h ;  ah = 7 (color attribute)
   293                              <1> 	;rep	stosw	
   294                              <1> 
   295                              <1> loc_rw_char:
   296 00007913 E899000000          <1> 	call	rw_char
   297                              <1> loc_move_command:
   298 00007918 BE[F65F0100]        <1> 	mov	esi, CommandBuffer
   299 0000791D 89F7                <1> 	mov	edi, esi
   300 0000791F 31C9                <1> 	xor	ecx, ecx
   301                              <1> first_command_char:
   302 00007921 AC                  <1> 	lodsb
   303 00007922 3C20                <1> 	cmp	al, 20h
   304 00007924 772E                <1> 	ja	short pass_space_control
   305 00007926 7241                <1> 	jb	short loc_move_cmd_arguments_ok
   306 00007928 81FE[45600100]      <1> 	cmp	esi, CommandBuffer + 79
   307 0000792E 72F1                <1> 	jb	short first_command_char
   308 00007930 EB37                <1> 	jmp	short loc_move_cmd_arguments_ok
   309                              <1> 
   310                              <1> next_command_char:
   311 00007932 AC                  <1> 	lodsb
   312 00007933 3C20                <1> 	cmp	al, 20h
   313 00007935 771D                <1> 	ja	short pass_space_control
   314 00007937 7230                <1> 	jb	short loc_move_cmd_arguments_ok
   315                              <1> 
   316                              <1> loc_1st_cmd_arg: ; 30/01/2016
   317 00007939 AC                  <1> 	lodsb
   318 0000793A 3C20                <1> 	cmp	al, 20h
   319 0000793C 74FB                <1> 	je	short loc_1st_cmd_arg
   320 0000793E 7229                <1> 	jb	short loc_move_cmd_arguments_ok
   321                              <1> 	
   322 00007940 C60700              <1>         mov     byte [edi], 0
   323 00007943 47                  <1> 	inc	edi
   324                              <1> 
   325                              <1> loc_move_cmd_arguments:
   326 00007944 AA                  <1> 	stosb
   327 00007945 81FE[45600100]      <1> 	cmp	esi, CommandBuffer + 79
   328 0000794B 731C                <1> 	jnb	short loc_move_cmd_arguments_ok
   329 0000794D AC                  <1>         lodsb
   330 0000794E 3C20                <1> 	cmp	al, 20h
   331 00007950 73F2                <1> 	jnb	short loc_move_cmd_arguments
   332 00007952 EB15                <1> 	jmp	short loc_move_cmd_arguments_ok
   333                              <1> 
   334                              <1> pass_space_control:
   335 00007954 3C61                <1> 	cmp	al, 61h
   336 00007956 7206                <1> 	jb	short pass_capitalize
   337 00007958 3C7A                <1> 	cmp	al, 7Ah
   338 0000795A 7702                <1> 	ja	short pass_capitalize
   339 0000795C 24DF                <1> 	and	al, 0DFh
   340                              <1> pass_capitalize:
   341 0000795E AA                  <1> 	stosb   
   342 0000795F FEC1                <1> 	inc     cl
   343 00007961 81FE[45600100]      <1>         cmp     esi, CommandBuffer + 79
   344 00007967 72C9                <1> 	jb      short next_command_char 
   345                              <1> 
   346                              <1> loc_move_cmd_arguments_ok:
   347 00007969 C60700              <1>         mov     byte [edi], 0
   348                              <1> 
   349                              <1> call_command_interpreter:
   350 0000796C E8CF080000          <1> 	call    command_interpreter
   351                              <1> 
   352                              <1> return_from_cmd_interpreter:
   353 00007971 B950000000          <1>         mov	ecx, 80
   354                              <1> 	;mov	cx, 80
   355 00007976 BF[F65F0100]        <1> 	mov	edi, CommandBuffer
   356 0000797B 30C0                <1> 	xor	al, al
   357 0000797D F3AA                <1> 	rep	stosb
   358                              <1> 	;cmp	byte [Program_Exit], 0
   359                              <1> 	;ja	short loc_terminate_trdos
   360                              <1>         
   361                              <1> 	; 16/01/2016
   362 0000797F 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3 ; 80*25 color
   363 00007986 741D                <1> 	je	short pass_set_txt_mode
   364                              <1> 
   365 00007988 E8D89FFFFF          <1> 	call	set_txt_mode ; set vide mode to 03h
   366                              <1> 	; 07/01/2017
   367 0000798D 30C0                <1> 	xor	al, al
   368                              <1> 
   369                              <1> loc_check_active_page:
   370                              <1> 	;xor	al, al
   371 0000798F 3805[AE5E0100]      <1> 	cmp	[ACTIVE_PAGE], al ; 0
   372 00007995 0F842CFFFFFF        <1>         je      loc_TRDOS_prompt 
   373                              <1> 	; AL = 0 = video page 0
   374 0000799B E8DEA3FFFF          <1> 	call	set_active_page
   375 000079A0 E922FFFFFF          <1>         jmp     loc_TRDOS_prompt ; infinitive loop
   376                              <1> 
   377                              <1> pass_set_txt_mode: 
   378 000079A5 BE[631F0100]        <1> 	mov	esi, nextline
   379 000079AA E856F2FFFF          <1> 	call	print_msg
   380 000079AF EBDE                <1> 	jmp     short loc_check_active_page
   381                              <1> 
   382                              <1> rw_char:
   383                              <1> 	; 13/05/2016
   384                              <1> 	; 30/01/2016
   385                              <1> 	; 29/01/2016
   386                              <1> 	; 17/01/2016 (TRDOS 386 = TRDOS v2.0)
   387                              <1> 	; 2004-2005
   388                              <1> 	
   389                              <1> 	; DH = cursor row, DL = cursor column
   390                              <1> 	; BH = 0 = video page number (active page)
   391                              <1> 
   392                              <1> 	;xor	bh, bh ; 0 = video page 0
   393                              <1> 
   394                              <1> readnextchar:
   395 000079B1 30E4                <1> 	xor     ah, ah
   396 000079B3 E8A294FFFF          <1> 	call	int16h
   397 000079B8 20C0                <1> 	and	al, al
   398 000079BA 7432                <1> 	jz	short loc_arrow    
   399 000079BC 3CE0                <1> 	cmp	al, 0E0h          
   400 000079BE 742E                <1> 	je	short loc_arrow
   401 000079C0 3C08                <1> 	cmp	al, 08h             
   402 000079C2 7542                <1> 	jne	short char_return
   403                              <1> loc_back:
   404 000079C4 3A15[A65F0100]      <1> 	cmp	dl, [CursorColumn]
   405 000079CA 76E5                <1> 	jna     short readnextchar
   406                              <1> prev_column:
   407 000079CC FECA                <1> 	dec	dl
   408                              <1> set_cursor_pos:
   409                              <1> 	;push	dx
   410 000079CE 52                  <1> 	push	edx ; 29/12/2017
   411                              <1> 	;xor	bh, bh ; 0 = video page 0
   412                              <1> 	; DH = Row, DL = Column
   413 000079CF E89FA7FFFF          <1> 	call	_set_cpos ; 17/01/2016
   414 000079D4 5A                  <1>         pop	edx ; 29/12/2017
   415                              <1> 	;pop	dx
   416                              <1> 	;movzx	ebx, dl
   417 000079D5 88D3                <1> 	mov	bl, dl
   418 000079D7 2A1D[A65F0100]      <1> 	sub	bl, [CursorColumn] 
   419 000079DD B020                <1> 	mov	al, 20h
   420 000079DF 8883[F65F0100]      <1> 	mov	[CommandBuffer+ebx], al
   421                              <1> 	;sub	bh, bh ; video page 0
   422                              <1> 	;mov	cx, 1
   423 000079E5 B307                <1> 	mov	bl, 7 ; color attribute
   424 000079E7 E862A6FFFF          <1> 	call	_write_c_current ; 17/01/2016
   425                              <1> 	;mov	dx, [CURSOR_POSN]
   426 000079EC EBC3                <1> 	jmp	short readnextchar
   427                              <1> loc_arrow:    
   428 000079EE 80FC4B              <1> 	cmp	ah, 4Bh
   429 000079F1 74D1                <1> 	je	short loc_back
   430 000079F3 80FC53              <1> 	cmp	ah, 53h
   431 000079F6 74CC                <1> 	je      short loc_back
   432 000079F8 80FC4D              <1> 	cmp	ah, 4Dh
   433 000079FB 75B4                <1> 	jne	short readnextchar
   434 000079FD 80FA4F              <1> 	cmp	dl, 79
   435 00007A00 73AF                <1> 	jnb	short readnextchar
   436 00007A02 FEC2                <1> 	inc	dl
   437 00007A04 EBC8                <1> 	jmp	short set_cursor_pos
   438                              <1> char_return:
   439 00007A06 0FB6DA              <1> 	movzx	ebx, dl
   440 00007A09 2A1D[A65F0100]      <1> 	sub	bl, [CursorColumn] 
   441 00007A0F 3C20                <1> 	cmp	al, 20h
   442 00007A11 721D                <1> 	jb	short loc_escape
   443 00007A13 8883[F65F0100]      <1> 	mov	[CommandBuffer+ebx], al
   444 00007A19 80FA4F              <1> 	cmp	dl, 79
   445 00007A1C 7393                <1> 	jnb	short readnextchar
   446 00007A1E 66BB0700            <1> 	mov	bx, 7 ; color attribute
   447 00007A22 E8AEA6FFFF          <1> 	call	_write_tty
   448 00007A27 668B15[9E5E0100]    <1> 	mov	dx, [CURSOR_POSN] ; video page 0
   449 00007A2E EB81                <1>         jmp     readnextchar
   450                              <1> loc_escape:
   451 00007A30 3C1B                <1> 	cmp	al, 1Bh
   452 00007A32 7418                <1> 	je	short rw_char_retn
   453                              <1> 	;
   454 00007A34 3C0D                <1> 	cmp	al, 0Dh ; CR
   455 00007A36 0F8575FFFFFF        <1>         jne     readnextchar
   456                              <1> 	; 13/05/2016
   457 00007A3C 66BB0700            <1> 	mov	bx, 7 ; attribute/color (bl)
   458                              <1> 		      ; video page 0 (bh=0)	
   459 00007A40 E890A6FFFF          <1> 	call	_write_tty
   460                              <1> 	;mov	bx, 7  ; attribute/color
   461                              <1> 		      ; video page 0 (bh=0)
   462 00007A45 B00A                <1> 	mov	al, 0Ah ; LF
   463 00007A47 E889A6FFFF          <1> 	call	_write_tty
   464                              <1> rw_char_retn:
   465 00007A4C C3                  <1> 	retn
   466                              <1> 
   467                              <1> show_date:
   468                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   469                              <1>         ; 2004-2005
   470                              <1> 
   471                              <1> 	;mov	ah, 04h
   472                              <1> 	;call	int1Ah
   473 00007A4D E878E7FFFF          <1> 	call	RTC_40	; GET RTC DATE
   474                              <1> 
   475 00007A52 88D0                <1> 	mov	al, dl
   476 00007A54 E8F893FFFF          <1>   	call	bcd_to_ascii
   477 00007A59 66A3[06140100]      <1> 	mov	[Day], ax
   478                              <1> 
   479 00007A5F 88F0                <1> 	mov	al, dh
   480 00007A61 E8EB93FFFF          <1>   	call	bcd_to_ascii
   481 00007A66 66A3[09140100]      <1> 	mov	[Month], ax
   482                              <1> 
   483 00007A6C 88E8                <1> 	mov	al, ch
   484 00007A6E E8DE93FFFF          <1>   	call	bcd_to_ascii
   485 00007A73 66A3[0C140100]      <1> 	mov	[Century], ax
   486                              <1> 
   487 00007A79 88C8                <1> 	mov	al, cl
   488 00007A7B E8D193FFFF          <1>   	call	bcd_to_ascii
   489 00007A80 66A3[0E140100]      <1> 	mov	word [Year], ax
   490                              <1> 
   491 00007A86 BE[F6130100]        <1> 	mov	esi, Msg_Show_Date
   492 00007A8B E875F1FFFF          <1> 	call	print_msg
   493                              <1> 
   494 00007A90 C3                  <1> 	retn
   495                              <1> 
   496                              <1> set_date:
   497                              <1> 	; 13/05/2016
   498                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   499                              <1>         ; 2004-2005
   500                              <1> 
   501 00007A91 BE[DA130100]        <1> 	mov	esi, Msg_Enter_Date
   502 00007A96 E86AF1FFFF          <1> 	call	print_msg
   503                              <1> 
   504                              <1> loc_enter_day_1:
   505 00007A9B 30E4                <1> 	xor     ah, ah
   506 00007A9D E8B893FFFF          <1> 	call	int16h
   507                              <1> 	; AL = ASCII Code of the Character
   508 00007AA2 3C0D                <1> 	cmp	al, 13
   509 00007AA4 0F84B7010000        <1> 	je	loc_set_date_retn
   510 00007AAA 3C1B                <1> 	cmp	al, 27
   511 00007AAC 0F84AF010000        <1> 	je	loc_set_date_retn
   512 00007AB2 A2[06140100]        <1> 	mov	[Day], al
   513 00007AB7 3C30                <1> 	cmp	al, '0'
   514 00007AB9 0F82AD010000        <1> 	jb	loc_set_date_stc_0
   515 00007ABF 3C33                <1> 	cmp	al, '3'
   516 00007AC1 0F87A5010000        <1> 	ja	loc_set_date_stc_0
   517                              <1> 	; 13/05/2016
   518                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   519                              <1> 		      ; video page 0 (bh)	
   520 00007AC7 B307                <1> 	mov	bl, 7
   521 00007AC9 E807A6FFFF          <1> 	call	_write_tty
   522                              <1> loc_enter_day_2:
   523 00007ACE 30E4                <1> 	xor     ah, ah
   524 00007AD0 E88593FFFF          <1> 	call	int16h
   525                              <1> 	; AL = ASCII Code of the Character
   526 00007AD5 3C1B                <1> 	cmp	al, 27
   527 00007AD7 0F8484010000        <1>         je      loc_set_date_retn
   528 00007ADD A2[07140100]        <1> 	mov	[Day+1], al
   529 00007AE2 3C30                <1> 	cmp	al, '0'
   530 00007AE4 0F828C010000        <1>         jb      loc_set_date_stc_1
   531 00007AEA 3C39                <1> 	cmp	al, '9'
   532 00007AEC 0F8784010000        <1>         ja      loc_set_date_stc_1
   533 00007AF2 803D[06140100]33    <1> 	cmp	byte [Day], '3'
   534 00007AF9 7208                <1> 	jb	short pass_set_day_31
   535 00007AFB 3C31                <1> 	cmp	al, '1'
   536 00007AFD 0F8773010000        <1>         ja      loc_set_date_stc_1
   537                              <1> pass_set_day_31:
   538                              <1> 	; 13/05/2016
   539                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   540                              <1> 		      ; video page 0 (bh)	
   541 00007B03 B307                <1> 	mov	bl, 7
   542 00007B05 E8CBA5FFFF          <1> 	call	_write_tty
   543                              <1> loc_enter_separator_1:
   544 00007B0A 28E4                <1> 	sub     ah, ah ; 0
   545 00007B0C E84993FFFF          <1> 	call	int16h
   546                              <1> 	; AL = ASCII Code of the Character
   547 00007B11 3C1B                <1> 	cmp	al, 27
   548 00007B13 0F8448010000        <1>         je      loc_set_date_retn
   549 00007B19 3C2D                <1> 	cmp	al, '-'
   550 00007B1B 7408                <1> 	je	short pass_set_date_separator_1
   551 00007B1D 3C2F                <1> 	cmp	al, '/'
   552 00007B1F 0F856C010000        <1>         jne     loc_set_date_stc_2
   553                              <1> pass_set_date_separator_1:
   554                              <1> 	; 13/05/2016
   555                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   556                              <1> 		      ; video page 0 (bh)
   557 00007B25 B307                <1> 	mov	bl, 7	
   558 00007B27 E8A9A5FFFF          <1> 	call	_write_tty
   559                              <1> loc_enter_month_1:
   560 00007B2C 30E4                <1> 	xor     ah, ah ; 0
   561 00007B2E E82793FFFF          <1> 	call	int16h
   562                              <1> 	; AL = ASCII Code of the Character
   563 00007B33 3C1B                <1> 	cmp	al, 27
   564 00007B35 0F8426010000        <1>         je      loc_set_date_retn
   565 00007B3B A2[09140100]        <1> 	mov	[Month], al
   566 00007B40 3C30                <1> 	cmp	al, '0'
   567 00007B42 0F8264010000        <1>         jb      loc_set_date_stc_3
   568 00007B48 3C31                <1> 	cmp	al, '1'
   569 00007B4A 0F875C010000        <1>         ja      loc_set_date_stc_3
   570                              <1> 	; 13/05/2016
   571                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   572                              <1> 		      ; video page 0 (bh)	
   573 00007B50 B307                <1> 	mov	bl, 7
   574 00007B52 E87EA5FFFF          <1> 	call	_write_tty
   575                              <1> loc_enter_month_2:
   576 00007B57 30E4                <1> 	xor     ah, ah
   577 00007B59 E8FC92FFFF          <1> 	call	int16h
   578                              <1> 	; AL = ASCII Code of the Character
   579 00007B5E 3C1B                <1> 	cmp	al, 27
   580 00007B60 0F84FB000000        <1>         je      loc_set_date_retn
   581 00007B66 A2[0A140100]        <1> 	mov	[Month+1], al
   582 00007B6B 3C30                <1> 	cmp	al, '0'
   583 00007B6D 0F8254010000        <1>         jb      loc_set_date_stc_4
   584 00007B73 3C39                <1> 	cmp	al, '9'
   585 00007B75 0F874C010000        <1>         ja      loc_set_date_stc_4
   586 00007B7B 803D[09140100]31    <1> 	cmp	byte [Month], '1'
   587 00007B82 7208                <1> 	jb	short pass_set_month_12
   588 00007B84 3C32                <1> 	cmp	al, '2'
   589 00007B86 0F873B010000        <1>         ja      loc_set_date_stc_4
   590                              <1> pass_set_month_12:
   591                              <1> 	; 13/05/2016
   592                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   593                              <1> 		      ; video page 0 (bh)
   594 00007B8C B307                <1> 	mov	bl, 7	
   595 00007B8E E842A5FFFF          <1> 	call	_write_tty
   596                              <1> loc_enter_separator_2:
   597 00007B93 28E4                <1> 	sub     ah, ah
   598 00007B95 E8C092FFFF          <1> 	call	int16h
   599                              <1> 	; AL = ASCII Code of the Character
   600 00007B9A 3C1B                <1> 	cmp	al, 27
   601 00007B9C 0F84BF000000        <1>         je      loc_set_date_retn
   602 00007BA2 3C2D                <1> 	cmp	al, '-'
   603 00007BA4 7408                <1> 	je	short pass_set_date_separator_2
   604 00007BA6 3C2F                <1> 	cmp	al, '/'
   605 00007BA8 0F8534010000        <1>         jne     loc_set_date_stc_5
   606                              <1> pass_set_date_separator_2:
   607                              <1> 	; 13/05/2016
   608                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   609                              <1> 		      ; video page 0 (bh)	
   610 00007BAE B307                <1> 	mov	bl, 7
   611 00007BB0 E820A5FFFF          <1> 	call	_write_tty
   612                              <1> loc_enter_year_1:
   613 00007BB5 30E4                <1> 	xor    ah, ah
   614 00007BB7 E89E92FFFF          <1> 	call	int16h
   615                              <1> 	; AL = ASCII Code of the Character
   616 00007BBC 3C1B                <1> 	cmp	al, 27
   617 00007BBE 0F849D000000        <1>         je      loc_set_date_retn
   618 00007BC4 A2[0E140100]        <1> 	mov	[Year], al
   619 00007BC9 3C30                <1> 	cmp	al, '0'
   620 00007BCB 0F822C010000        <1>         jb      loc_set_date_stc_6
   621 00007BD1 3C39                <1> 	cmp	al, '9'
   622 00007BD3 0F8724010000        <1>         ja      loc_set_date_stc_6
   623                              <1> 	; 13/05/2016
   624                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   625                              <1> 		      ; video page 0 (bh)
   626 00007BD9 B307                <1> 	mov	bl, 7	
   627 00007BDB E8F5A4FFFF          <1> 	call	_write_tty
   628                              <1> loc_enter_year_2:
   629 00007BE0 30E4                <1> 	xor	ah, ah
   630 00007BE2 E87392FFFF          <1> 	call	int16h
   631                              <1> 	; AL = ASCII Code of the Character
   632 00007BE7 3C1B                <1> 	cmp	al, 27
   633 00007BE9 7476                <1> 	je	short loc_set_date_retn
   634 00007BEB A2[0F140100]        <1> 	mov	byte [Year+1], al
   635 00007BF0 3C30                <1> 	cmp	al, '0'
   636 00007BF2 0F8220010000        <1>         jb      loc_set_date_stc_7
   637 00007BF8 3C39                <1> 	cmp	al, '9'
   638 00007BFA 0F8718010000        <1>         ja      loc_set_date_stc_7
   639                              <1> 	; 13/05/2016
   640                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   641                              <1> 		      ; video page 0 (bh)
   642 00007C00 B307                <1> 	mov	bl, 7	
   643 00007C02 E8CEA4FFFF          <1> 	call	_write_tty
   644                              <1> loc_set_date_get_lchar_again:
   645 00007C07 28E4                <1> 	sub	ah, ah ; 0
   646 00007C09 E84C92FFFF          <1> 	call	int16h
   647                              <1> 	; AL = ASCII Code of the Character
   648 00007C0E 3C0D                <1> 	cmp	al, 13 ; ENTER key
   649 00007C10 7412                <1> 	je	short loc_set_date_progress
   650 00007C12 3C1B                <1> 	cmp	al, 27 ; ESC key
   651 00007C14 744B                <1> 	je	short loc_set_date_retn
   652                              <1> 	;
   653 00007C16 E82A010000          <1> 	call	check_for_backspace
   654 00007C1B 75EA                <1> 	jne	short loc_set_date_get_lchar_again
   655                              <1> 
   656                              <1> loc_set_date_bs_8:
   657 00007C1D E811010000          <1> 	call	write_backspace
   658 00007C22 EBBC                <1> 	jmp	short loc_enter_year_2
   659                              <1> 
   660                              <1> loc_set_date_progress:
   661                              <1> 	; Get Current Date
   662                              <1> 	;mov	ah, 04h
   663                              <1> 	;call	int1Ah
   664 00007C24 E8A1E5FFFF          <1> 	call	RTC_40	; GET RTC DATE
   665                              <1> 	; CH = century (in BCD)
   666                              <1> 
   667 00007C29 66A1[0E140100]      <1> 	mov	ax, [Year]
   668 00007C2F 662D3030            <1> 	sub	ax, '00'
   669 00007C33 C0E004              <1> 	shl	al, 4 ; * 16
   670 00007C36 88C1                <1> 	mov	cl, al
   671 00007C38 00E1                <1> 	add	cl, ah
   672 00007C3A 66A1[09140100]      <1> 	mov	ax, [Month]
   673 00007C40 662D3030            <1> 	sub	ax, '00'
   674 00007C44 C0E004              <1> 	shl	al, 4 ; * 16
   675 00007C47 88C6                <1> 	mov	dh, al
   676 00007C49 00E6                <1> 	add	dh, ah
   677 00007C4B 66A1[06140100]      <1> 	mov	ax, [Day]
   678 00007C51 662D3030            <1> 	sub	ax, '00'
   679 00007C55 C0E004              <1> 	shl	al, 4 ; * 16
   680 00007C58 88C2                <1> 	mov	dl, al
   681 00007C5A 00E2                <1> 	add	dl, ah
   682                              <1> 
   683                              <1> 	;mov	ah, 05h
   684                              <1> 	;call	int1Ah
   685 00007C5C E896E5FFFF          <1> 	call	RTC_50	; SET RTC DATE
   686                              <1> 
   687                              <1> loc_set_date_retn:
   688 00007C61 BE[631F0100]        <1> 	mov	esi, nextline
   689 00007C66 E89AEFFFFF          <1> 	call	print_msg
   690 00007C6B C3                  <1> 	retn
   691                              <1> 
   692                              <1> loc_set_date_stc_0:
   693                              <1> 	;xor	bh, bh ; video page 0
   694 00007C6C E84CA5FFFF          <1> 	call	beeper ; BEEP !
   695 00007C71 E925FEFFFF          <1>         jmp     loc_enter_day_1
   696                              <1> loc_set_date_stc_1:
   697 00007C76 E8CA000000          <1> 	call	check_for_backspace
   698 00007C7B 740A                <1> 	je	short loc_set_date_bs_1
   699                              <1> 	;xor	bh, bh ; video page 0
   700 00007C7D E83BA5FFFF          <1> 	call	beeper ; BEEP !
   701 00007C82 E947FEFFFF          <1>         jmp     loc_enter_day_2
   702                              <1> loc_set_date_bs_1:
   703 00007C87 E8A7000000          <1> 	call	write_backspace
   704 00007C8C E90AFEFFFF          <1>         jmp     loc_enter_day_1
   705                              <1> loc_set_date_stc_2:
   706 00007C91 E8AF000000          <1> 	call	check_for_backspace
   707 00007C96 740A                <1> 	je	short loc_set_date_bs_2
   708                              <1> 	;xor	bh, bh ; video page 0
   709 00007C98 E820A5FFFF          <1> 	call	beeper ; BEEP !
   710 00007C9D E968FEFFFF          <1>         jmp     loc_enter_separator_1
   711                              <1> loc_set_date_bs_2:
   712 00007CA2 E88C000000          <1> 	call	write_backspace
   713 00007CA7 E922FEFFFF          <1>         jmp     loc_enter_day_2
   714                              <1> loc_set_date_stc_3:
   715 00007CAC E894000000          <1> 	call	check_for_backspace	
   716 00007CB1 740A                <1> 	je short loc_set_date_bs_3
   717                              <1> 	;xor	bh, bh ; video page 0
   718 00007CB3 E805A5FFFF          <1> 	call	beeper ; BEEP !
   719 00007CB8 E96FFEFFFF          <1>         jmp     loc_enter_month_1
   720                              <1> loc_set_date_bs_3:
   721 00007CBD E871000000          <1> 	call	write_backspace
   722 00007CC2 E943FEFFFF          <1>         jmp     loc_enter_separator_1
   723                              <1> loc_set_date_stc_4:
   724 00007CC7 E879000000          <1> 	call	check_for_backspace	
   725 00007CCC 740A                <1> 	je	short loc_set_date_bs_4
   726                              <1> 	;xor	bh, bh ; video page 0
   727 00007CCE E8EAA4FFFF          <1> 	call	beeper ; BEEP !
   728 00007CD3 E97FFEFFFF          <1>         jmp     loc_enter_month_2
   729                              <1> loc_set_date_bs_4:
   730 00007CD8 E856000000          <1> 	call	write_backspace
   731 00007CDD E94AFEFFFF          <1>         jmp     loc_enter_month_1
   732                              <1> loc_set_date_stc_5:
   733 00007CE2 E85E000000          <1> 	call	check_for_backspace
   734 00007CE7 740A                <1> 	je	short loc_set_date_bs_5
   735                              <1> 	;xor	bh, bh ; video page 0
   736 00007CE9 E8CFA4FFFF          <1> 	call	beeper ; BEEP !
   737 00007CEE E9A0FEFFFF          <1>         jmp     loc_enter_separator_2
   738                              <1> loc_set_date_bs_5:
   739 00007CF3 E83B000000          <1> 	call	write_backspace
   740 00007CF8 E95AFEFFFF          <1>         jmp     loc_enter_month_2
   741                              <1> loc_set_date_stc_6:
   742 00007CFD E843000000          <1> 	call	check_for_backspace
   743 00007D02 740A                <1>         je      short  loc_set_date_bs_6
   744                              <1> 	;xor	bh, bh ; video page 0
   745 00007D04 E8B4A4FFFF          <1> 	call	beeper ; BEEP !
   746 00007D09 E9A7FEFFFF          <1>         jmp     loc_enter_year_1
   747                              <1> loc_set_date_bs_6:
   748 00007D0E E820000000          <1> 	call	write_backspace
   749 00007D13 E97BFEFFFF          <1>         jmp     loc_enter_separator_2
   750                              <1> loc_set_date_stc_7:
   751 00007D18 E828000000          <1> 	call	check_for_backspace
   752 00007D1D 740A                <1> 	je	short loc_set_date_bs_7
   753                              <1> 	;xor	bh, bh ; video page 0
   754 00007D1F E899A4FFFF          <1> 	call	beeper ; BEEP !
   755 00007D24 E9B7FEFFFF          <1>         jmp     loc_enter_year_2
   756                              <1> loc_set_date_bs_7:
   757 00007D29 E805000000          <1> 	call	write_backspace
   758 00007D2E E982FEFFFF          <1>         jmp     loc_enter_year_1
   759                              <1> 
   760                              <1> write_backspace:
   761                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   762 00007D33 B008                <1> 	mov	al, 08h ; BACKSPACE
   763                              <1> 	; 13/05/2016
   764 00007D35 66BB0700            <1> 	mov	bx, 7 ; bl = attribute/color
   765                              <1> 		      ; bh = video page = 0	
   766 00007D39 E897A3FFFF          <1> 	call	_write_tty
   767 00007D3E B020                <1> 	mov	al, 20h ; BLANK/SPACE char 
   768                              <1> 	;mov	bx, 7 ; attribute/color
   769                              <1> 	;call	_write_c_current
   770                              <1> 	;retn
   771 00007D40 E909A3FFFF          <1> 	jmp	_write_c_current
   772                              <1> 
   773                              <1> check_for_backspace:
   774                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   775 00007D45 663D080E            <1> 	cmp	ax, 0E08h
   776 00007D49 7410                <1> 	je	short cfbs_retn
   777 00007D4B 663DE04B            <1> 	cmp	ax, 4BE0h
   778 00007D4F 740A                <1> 	je	short cfbs_retn
   779 00007D51 663D004B            <1> 	cmp	ax, 4B00h
   780 00007D55 7404                <1> 	je	short cfbs_retn
   781 00007D57 663DE053            <1> 	cmp	ax, 53E0h
   782                              <1> cfbs_retn:
   783 00007D5B C3                  <1> 	retn
   784                              <1> 
   785                              <1> show_time:
   786                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   787                              <1>         ; 2004-2005
   788                              <1> 
   789                              <1> 	;mov	ah, 02h
   790                              <1> 	;call	int1Ah
   791 00007D5C E8F8E3FFFF          <1> 	call	RTC_20	; GET RTC TIME
   792                              <1> 	
   793 00007D61 88E8                <1> 	mov	al, ch
   794 00007D63 E8E990FFFF          <1> 	call	bcd_to_ascii
   795 00007D68 66A3[34140100]      <1> 	mov	[Hour], ax
   796                              <1> 
   797 00007D6E 88C8                <1> 	mov	al, cl
   798 00007D70 E8DC90FFFF          <1> 	call	bcd_to_ascii
   799 00007D75 66A3[37140100]      <1> 	mov	[Minute], ax
   800                              <1> 
   801 00007D7B 88F0                <1> 	mov	al, dh
   802 00007D7D E8CF90FFFF          <1> 	call	bcd_to_ascii
   803 00007D82 66A3[3A140100]      <1> 	mov	[Second], ax
   804                              <1> 
   805 00007D88 BE[24140100]        <1> 	mov	esi, Msg_Show_Time
   806 00007D8D E873EEFFFF          <1> 	call	print_msg
   807 00007D92 C3                  <1> 	retn
   808                              <1> 
   809                              <1> set_time:
   810                              <1> 	; 13/05/2016
   811                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
   812                              <1>         ; 2004-2005
   813                              <1> 
   814 00007D93 BE[13140100]        <1> 	mov 	esi, Msg_Enter_Time
   815 00007D98 E868EEFFFF          <1> 	call	print_msg
   816                              <1> 
   817                              <1> loc_enter_hour_1:
   818 00007D9D 30E4                <1> 	xor     ah, ah
   819 00007D9F E8B690FFFF          <1> 	call	int16h
   820                              <1> 	; AL = ASCII Code of the Character
   821 00007DA4 3C0D                <1> 	cmp	al, 13 ; ENTER key
   822 00007DA6 0F84AE010000        <1>         je      loc_set_time_retn
   823 00007DAC 3C1B                <1> 	cmp	al, 27 ; ESC key
   824 00007DAE 0F84A6010000        <1>         je      loc_set_time_retn
   825 00007DB4 A2[34140100]        <1> 	mov	[Hour], al
   826 00007DB9 3C30                <1> 	cmp	al, '0'
   827 00007DBB 0F82A4010000        <1>         jb      loc_set_time_stc_0
   828 00007DC1 3C32                <1> 	cmp	al, '2'
   829 00007DC3 0F879C010000        <1>         ja      loc_set_time_stc_0
   830                              <1> 	; 13/05/2016
   831                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   832                              <1> 		      ; video page 0 (bh)
   833 00007DC9 B307                <1> 	mov	bl, 7	
   834 00007DCB E805A3FFFF          <1> 	call	_write_tty
   835                              <1> loc_enter_hour_2:
   836 00007DD0 30E4                <1> 	xor     ah, ah
   837 00007DD2 E88390FFFF          <1> 	call	int16h
   838                              <1> 	; AL = ASCII Code of the Character
   839 00007DD7 3C1B                <1> 	cmp	al, 27
   840 00007DD9 0F847B010000        <1>         je      loc_set_time_retn
   841 00007DDF A2[35140100]        <1> 	mov	[Hour+1], al
   842 00007DE4 3C30                <1> 	cmp	al, '0'
   843 00007DE6 0F8283010000        <1>         jb      loc_set_time_stc_1
   844 00007DEC 3C39                <1> 	cmp	al, '9'
   845 00007DEE 0F877B010000        <1> 	ja	loc_set_time_stc_1
   846 00007DF4 803D[34140100]32    <1>         cmp     byte [Hour], '2'
   847 00007DFB 7208                <1> 	jb	short pass_set_time_24
   848 00007DFD 3C34                <1> 	cmp	al, '4'
   849 00007DFF 0F876A010000        <1>         ja      loc_set_time_stc_1
   850                              <1> pass_set_time_24:
   851                              <1> 	; 13/05/2016
   852                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   853                              <1> 		      ; video page 0 (bh)
   854 00007E05 B307                <1> 	mov	bl, 7	
   855 00007E07 E8C9A2FFFF          <1> 	call	_write_tty
   856                              <1> loc_enter_time_separator_1:
   857 00007E0C 28E4                <1> 	sub    ah, ah ; 0
   858 00007E0E E84790FFFF          <1> 	call	int16h
   859                              <1> 	; AL = ASCII Code of the Character
   860 00007E13 3C1B                <1> 	cmp	al, 27
   861 00007E15 0F843F010000        <1>         je      loc_set_time_retn
   862 00007E1B 3C3A                <1> 	cmp	al, ':'
   863 00007E1D 0F8567010000        <1>         jne     loc_set_time_stc_2
   864                              <1> 	; 13/05/2016
   865                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   866                              <1> 		      ; video page 0 (bh)
   867 00007E23 B307                <1> 	mov	bl, 7	
   868 00007E25 E8ABA2FFFF          <1> 	call	_write_tty
   869                              <1> loc_enter_minute_1:
   870 00007E2A 30E4                <1> 	xor     ah, ah
   871 00007E2C E82990FFFF          <1> 	call	int16h
   872                              <1> 	; AL = ASCII Code of the Character
   873 00007E31 3C1B                <1> 	cmp	al, 27
   874 00007E33 0F8421010000        <1>         je      loc_set_time_retn
   875 00007E39 A2[37140100]        <1> 	mov	[Minute], al
   876 00007E3E 3C30                <1> 	cmp	al, '0'
   877 00007E40 0F825F010000        <1>         jb      loc_set_time_stc_3
   878 00007E46 3C35                <1> 	cmp	al, '5'
   879 00007E48 0F8757010000        <1>         ja      loc_set_time_stc_3
   880                              <1> 	; 13/05/2016
   881                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   882                              <1> 		      ; video page 0 (bh)
   883 00007E4E B307                <1> 	mov	bl, 7	
   884 00007E50 E880A2FFFF          <1> 	call	_write_tty
   885                              <1> loc_enter_minute_2:
   886 00007E55 30E4                <1> 	xor     ah, ah
   887 00007E57 E8FE8FFFFF          <1> 	call	int16h
   888                              <1> 	; AL = ASCII Code of the Character
   889 00007E5C 3C1B                <1> 	cmp	al, 27
   890 00007E5E 0F84F6000000        <1>         je      loc_set_time_retn
   891 00007E64 A2[38140100]        <1> 	mov	[Minute+1], al
   892 00007E69 3C30                <1> 	cmp	al, '0'
   893 00007E6B 0F824F010000        <1>         jb      loc_set_time_stc_4
   894 00007E71 3C39                <1> 	cmp	al, '9'
   895 00007E73 0F8747010000        <1>         ja      loc_set_time_stc_4
   896                              <1> 	; 13/05/2016
   897                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   898                              <1> 		      ; video page 0 (bh)
   899 00007E79 B307                <1> 	mov	bl, 7	
   900 00007E7B E855A2FFFF          <1> 	call	_write_tty
   901                              <1> loc_enter_time_separator_2:
   902 00007E80 66C705[3A140100]30- <1> 	mov	word [Second], 3030h
   902 00007E88 30                  <1>
   903 00007E89 28E4                <1> 	sub     ah, ah
   904 00007E8B E8CA8FFFFF          <1> 	call	int16h
   905                              <1> 	; AL = ASCII Code of the Character
   906 00007E90 3C0D                <1> 	cmp	al, 13
   907 00007E92 0F8485000000        <1>         je      loc_set_time_progress
   908 00007E98 3C1B                <1> 	cmp	al, 27
   909 00007E9A 0F84BA000000        <1>         je      loc_set_time_retn
   910 00007EA0 3C3A                <1> 	cmp	al, ':'
   911 00007EA2 0F8533010000        <1>         jne     loc_set_time_stc_5
   912                              <1> 	; 13/05/2016
   913                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   914                              <1> 		      ; video page 0 (bh)
   915 00007EA8 B307                <1> 	mov	bl, 7	
   916 00007EAA E826A2FFFF          <1> 	call	_write_tty
   917                              <1> loc_enter_second_1:
   918 00007EAF 30E4                <1> 	xor     ah, ah
   919 00007EB1 E8A48FFFFF          <1> 	call	int16h
   920                              <1> 	; AL = ASCII Code of the Character
   921 00007EB6 3C0D                <1> 	cmp	al, 13
   922 00007EB8 7463                <1> 	je	short loc_set_time_progress
   923 00007EBA 3C1B                <1> 	cmp	al, 27
   924 00007EBC 0F8498000000        <1>         je      loc_set_time_retn
   925 00007EC2 A2[3A140100]        <1> 	mov	[Second], al
   926 00007EC7 3C30                <1> 	cmp	al, '0'
   927 00007EC9 0F8227010000        <1>         jb      loc_set_time_stc_6
   928 00007ECF 3C35                <1> 	cmp	al, '5'
   929 00007ED1 0F871F010000        <1>         ja      loc_set_time_stc_6
   930                              <1> 	; 13/05/2016
   931                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   932                              <1> 		      ; video page 0 (bh)
   933 00007ED7 B307                <1> 	mov	bl, 7	
   934 00007ED9 E8F7A1FFFF          <1> 	call	_write_tty
   935                              <1> loc_enter_second_2:
   936 00007EDE 30E4                <1> 	xor     ah, ah
   937 00007EE0 E8758FFFFF          <1> 	call	int16h
   938                              <1> 	; AL = ASCII Code of the Character
   939 00007EE5 3C1B                <1> 	cmp	al, 27
   940 00007EE7 7471                <1> 	je	short loc_set_time_retn
   941 00007EE9 3C30                <1> 	cmp	al, '0'
   942 00007EEB 0F8229010000        <1>         jb      loc_set_time_stc_7
   943 00007EF1 3C39                <1> 	cmp	al, '9'
   944 00007EF3 0F8721010000        <1>         ja      loc_set_time_stc_7
   945                              <1> 	; 13/05/2016
   946                              <1> 	;mov	bx, 7 ; attribute/color (bl)
   947                              <1> 		      ; video page 0 (bh)
   948 00007EF9 B307                <1> 	mov	bl, 7	
   949 00007EFB E8D5A1FFFF          <1> 	call	_write_tty
   950                              <1> loc_set_time_get_lchar_again:
   951 00007F00 28E4                <1> 	sub	ah, ah ; 0
   952 00007F02 E8538FFFFF          <1> 	call	int16h
   953                              <1> 	; AL = ASCII Code of the Character
   954 00007F07 3C0D                <1> 	cmp	al, 13
   955 00007F09 7412                <1> 	je	short loc_set_time_progress
   956 00007F0B 3C1B                <1> 	cmp	al, 27
   957 00007F0D 744B                <1> 	je	short loc_set_time_retn
   958                              <1> 	;
   959 00007F0F E831FEFFFF          <1> 	call	check_for_backspace
   960 00007F14 75EA                <1> 	jne	short loc_set_time_get_lchar_again
   961                              <1> 
   962                              <1> loc_set_time_bs_8:
   963 00007F16 E818FEFFFF          <1> 	call	write_backspace
   964 00007F1B EBC1                <1> 	jmp	short loc_enter_second_2
   965                              <1> 
   966                              <1> loc_set_time_progress:
   967                              <1> 	; Get Current Time
   968                              <1> 	;mov 	ah, 02h
   969                              <1> 	;call	int1Ah
   970 00007F1D E837E2FFFF          <1> 	call	RTC_20	; GET RTC TIME
   971                              <1> 	;DL = Daylight Savings Enable option (0-1)	
   972                              <1> 
   973 00007F22 66A1[34140100]      <1> 	mov	ax, [Hour]
   974 00007F28 662D3030            <1> 	sub	ax, '00'
   975 00007F2C C0E004              <1> 	shl	al, 4 ; * 16
   976 00007F2F 88C5                <1> 	mov	ch, al
   977 00007F31 00E5                <1> 	add	ch, ah
   978 00007F33 66A1[37140100]      <1> 	mov	ax, [Minute]
   979 00007F39 662D3030            <1> 	sub	ax, '00'
   980 00007F3D C0E004              <1> 	shl	al, 4 ; * 16
   981 00007F40 88C1                <1> 	mov	cl, al
   982 00007F42 00E1                <1> 	add	cl, ah
   983 00007F44 66A1[3A140100]      <1> 	mov	ax, [Second]
   984 00007F4A 662D3030            <1> 	sub	ax, '00'
   985 00007F4E C0E004              <1> 	shl	al, 4 ; * 16
   986 00007F51 88C6                <1> 	mov	dh, al
   987 00007F53 00E6                <1> 	add	dh, ah
   988                              <1> 	
   989                              <1> 	;mov	ah, 03h
   990                              <1> 	;call	int1Ah
   991 00007F55 E82EE2FFFF          <1> 	call	RTC_30	; SET RTC TIME
   992                              <1> 
   993                              <1> loc_set_time_retn:
   994 00007F5A BE[631F0100]        <1> 	mov 	esi, nextline
   995 00007F5F E8A1ECFFFF          <1> 	call	print_msg
   996 00007F64 C3                  <1> 	retn
   997                              <1> 
   998                              <1> loc_set_time_stc_0:
   999                              <1> 	;xor	bh, bh ; video page 0
  1000 00007F65 E853A2FFFF          <1> 	call	beeper ; BEEP !
  1001 00007F6A E92EFEFFFF          <1>         jmp     loc_enter_hour_1
  1002                              <1> loc_set_time_stc_1:
  1003 00007F6F E8D1FDFFFF          <1> 	call	check_for_backspace
  1004 00007F74 740A                <1> 	je	short loc_set_time_bs_1
  1005                              <1> 	;xor	bh, bh ; video page 0
  1006 00007F76 E842A2FFFF          <1> 	call	beeper ; BEEP !
  1007 00007F7B E950FEFFFF          <1>         jmp     loc_enter_hour_2
  1008                              <1> loc_set_time_bs_1:
  1009 00007F80 E8AEFDFFFF          <1> 	call	write_backspace
  1010 00007F85 E913FEFFFF          <1>         jmp     loc_enter_hour_1
  1011                              <1> loc_set_time_stc_2:
  1012 00007F8A E8B6FDFFFF          <1> 	call	check_for_backspace
  1013 00007F8F 740A                <1> 	je	short loc_set_time_bs_2
  1014                              <1> 	;xor	bh, bh ; video page 0
  1015 00007F91 E827A2FFFF          <1> 	call	beeper ; BEEP !
  1016 00007F96 E971FEFFFF          <1>         jmp     loc_enter_time_separator_1
  1017                              <1> loc_set_time_bs_2:
  1018 00007F9B E893FDFFFF          <1> 	call	write_backspace
  1019 00007FA0 E92BFEFFFF          <1>         jmp     loc_enter_hour_2
  1020                              <1> loc_set_time_stc_3:
  1021 00007FA5 E89BFDFFFF          <1> 	call	check_for_backspace
  1022 00007FAA 740A                <1> 	je	short loc_set_time_bs_3
  1023                              <1> 	;xor	bh, bh ; video page 0
  1024 00007FAC E80CA2FFFF          <1> 	call	beeper ; BEEP !6
  1025 00007FB1 E974FEFFFF          <1>         jmp     loc_enter_minute_1
  1026                              <1> loc_set_time_bs_3:
  1027 00007FB6 E878FDFFFF          <1> 	call	write_backspace
  1028 00007FBB E94CFEFFFF          <1>         jmp     loc_enter_time_separator_1
  1029                              <1> loc_set_time_stc_4:
  1030 00007FC0 E880FDFFFF          <1> 	call	check_for_backspace
  1031 00007FC5 740A                <1> 	je	short loc_set_time_bs_4
  1032                              <1> 	;xor	bh, bh ; video page 0
  1033 00007FC7 E8F1A1FFFF          <1> 	call	beeper ; BEEP !
  1034 00007FCC E984FEFFFF          <1>         jmp     loc_enter_minute_2
  1035                              <1> loc_set_time_bs_4:
  1036 00007FD1 E85DFDFFFF          <1> 	call	write_backspace
  1037 00007FD6 E94FFEFFFF          <1>         jmp     loc_enter_minute_1
  1038                              <1> loc_set_time_stc_5:
  1039 00007FDB E865FDFFFF          <1> 	call	check_for_backspace
  1040 00007FE0 740A                <1> 	je	short loc_set_time_bs_5
  1041                              <1> 	;xor	bh, bh ; video page 0
  1042 00007FE2 E8D6A1FFFF          <1> 	call	beeper ; BEEP !
  1043 00007FE7 E994FEFFFF          <1>         jmp     loc_enter_time_separator_2
  1044                              <1> loc_set_time_bs_5:
  1045 00007FEC E842FDFFFF          <1> 	call	write_backspace
  1046 00007FF1 E95FFEFFFF          <1>         jmp     loc_enter_minute_2
  1047                              <1> loc_set_time_stc_6:
  1048 00007FF6 E84AFDFFFF          <1> 	call	check_for_backspace
  1049 00007FFB 7413                <1> 	je	short loc_set_time_bs_6
  1050                              <1> 	;xor	bh, bh ; video page 0
  1051 00007FFD E8BBA1FFFF          <1> 	call	beeper ; BEEP !
  1052 00008002 66C705[3A140100]30- <1> 	mov	word [Second], 3030h
  1052 0000800A 30                  <1>
  1053 0000800B E99FFEFFFF          <1>         jmp     loc_enter_second_1
  1054                              <1> loc_set_time_bs_6:
  1055 00008010 E81EFDFFFF          <1> 	call	write_backspace
  1056 00008015 E966FEFFFF          <1>         jmp     loc_enter_time_separator_2
  1057                              <1> loc_set_time_stc_7:
  1058 0000801A E826FDFFFF          <1> 	call	check_for_backspace
  1059 0000801F 740A                <1> 	je	short loc_set_time_bs_7
  1060                              <1> 	;xor	bh, bh ; video page 0
  1061 00008021 E897A1FFFF          <1> 	call	beeper ; BEEP !
  1062 00008026 E9B3FEFFFF          <1>         jmp     loc_enter_second_2
  1063                              <1> loc_set_time_bs_7:
  1064 0000802B E803FDFFFF          <1> 	call	write_backspace
  1065 00008030 E97AFEFFFF          <1>         jmp     loc_enter_second_1
  1066                              <1> 
  1067                              <1> print_volume_info:
  1068                              <1> 	; 01/03/2016
  1069                              <1> 	; 08/02/2016
  1070                              <1> 	; 06/02/2016
  1071                              <1> 	; 04/02/2016
  1072                              <1> 	; 18/01/2016 (TRDOS 386 = TRDOS v2.0)
  1073                              <1> 	; 25/10/2009
  1074                              <1> 	;
  1075                              <1> 	; "Volume Serial No: "
  1076                              <1>  	;
  1077                              <1> 	; INPUT  : AL = DOS Drive Number
  1078                              <1> 	; OUTPUT : AH = FS Type
  1079                              <1> 	;          AL = DOS Drive Name
  1080                              <1> 	; CF = 0 -> OK
  1081                              <1> 	; CF = 1 -> Drive not ready 
  1082                              <1> 
  1083 00008035 88C4                <1> 	mov	ah, al
  1084 00008037 28C0                <1> 	sub	al, al
  1085 00008039 0FB7F0              <1> 	movzx	esi, ax	
  1086 0000803C 81C600010900        <1> 	add	esi, Logical_DOSDisks
  1087 00008042 8A06                <1> 	mov	al, [esi]
  1088 00008044 3C41                <1> 	cmp	al, 'A'  
  1089 00008046 7304                <1> 	jnb	short loc_pvi_set_vol_name
  1090 00008048 8A6604              <1> 	mov	ah, [esi+LD_FSType]
  1091 0000804B C3                  <1> 	retn
  1092                              <1> 
  1093                              <1> loc_pvi_set_vol_name:
  1094 0000804C A2[6E140100]        <1> 	mov	[Vol_Drv_Name], al
  1095 00008051 56                  <1> 	push	esi
  1096 00008052 E858010000          <1> 	call	move_volume_name_and_serial_no ;;;
  1097 00008057 7302                <1> 	jnc	short loc_pvi_mvn_ok
  1098 00008059 5E                  <1> 	pop	esi
  1099 0000805A C3                  <1> 	retn
  1100                              <1> 
  1101                              <1> loc_pvi_mvn_ok:
  1102 0000805B 8B3424              <1> 	mov	esi, [esp]
  1103 0000805E 807E04A1            <1> 	cmp	byte [esi+LD_FSType], 0A1h
  1104 00008062 7509                <1> 	jne	short loc_pvi_fat_vol_size
  1105 00008064 8B4670              <1> 	mov	eax, [esi+LD_FS_VolumeSize]
  1106 00008067 0FB75E11            <1> 	movzx	ebx, word [esi+LD_FS_BytesPerSec]
  1107 0000806B EB07                <1> 	jmp	short loc_vol_size_mul32
  1108                              <1> loc_pvi_fat_vol_size:
  1109 0000806D 8B4670              <1> 	mov	eax, [esi+LD_TotalSectors]
  1110 00008070 0FB75E11            <1> 	movzx	ebx, word [esi+LD_BPB+BPB_BytsPerSec]
  1111                              <1> loc_vol_size_mul32:
  1112 00008074 F7E3                <1> 	mul	ebx
  1113 00008076 09D2                <1> 	or	edx, edx
  1114 00008078 7507                <1> 	jnz	short loc_vol_size_in_kbytes
  1115                              <1> loc_vol_size_in_bytes:
  1116 0000807A B9[4C140100]        <1> 	mov	ecx, VolSize_Bytes
  1117 0000807F EB0D                <1> 	jmp	short loc_write_vol_size_str
  1118                              <1> loc_vol_size_in_kbytes:
  1119 00008081 66BB0004            <1> 	mov	bx, 1024
  1120 00008085 F7F3                <1> 	div	ebx
  1121 00008087 B9[3F140100]        <1> 	mov 	ecx, VolSize_KiloBytes
  1122 0000808C 31D2                <1> 	xor	edx, edx ; 0
  1123                              <1> loc_write_vol_size_str:
  1124 0000808E 890D[7B660100]      <1> 	mov	[VolSize_Unit1], ecx
  1125                              <1> 	; 
  1126 00008094 BF[91660100]        <1> 	mov	edi, Vol_Tot_Sec_Str_End
  1127                              <1>         ;mov	byte [edi], 0
  1128 00008099 B90A000000          <1> 	mov	ecx, 10
  1129                              <1> loc_write_vol_size_chr:
  1130 0000809E F7F1                <1> 	div	ecx
  1131 000080A0 80C230              <1> 	add	dl, '0'
  1132 000080A3 4F                  <1> 	dec	edi	
  1133 000080A4 8817                <1> 	mov	[edi], dl
  1134 000080A6 85C0                <1> 	test	eax, eax
  1135 000080A8 7404                <1> 	jz	short loc_write_vol_size_str_ok
  1136 000080AA 28D2                <1> 	sub	dl, dl ; 0
  1137 000080AC EBF0                <1> 	jmp	short loc_write_vol_size_chr
  1138                              <1> 
  1139                              <1> loc_write_vol_size_str_ok:
  1140 000080AE 893D[83660100]      <1> 	mov	[Vol_Tot_Sec_Str_Start], edi
  1141                              <1> 	;
  1142 000080B4 BF[57140100]        <1> 	mov	edi, Vol_FS_Name
  1143 000080B9 8A4E03              <1> 	mov	cl, [esi+LD_FATType]
  1144 000080BC 20C9                <1> 	and	cl, cl ; 0 ?
  1145 000080BE 7515                <1> 	jnz	short loc_write_vol_FAT_str_1
  1146 000080C0 66C7075452          <1> 	mov	word [edi], 'TR'
  1147 000080C5 C7470420465331      <1> 	mov	dword [edi+4], ' FS1'
  1148                              <1> 	;movzx	ebx, word [esi+LD_FS_BytesPerSec]
  1149 000080CC 668B5E11            <1> 	mov	bx, [esi+LD_FS_BytesPerSec]
  1150 000080D0 8B4674              <1> 	mov	eax, [esi+LD_FS_FreeSectors]
  1151 000080D3 EB36                <1> 	jmp	short loc_vol_freespace_mul32
  1152                              <1> 
  1153                              <1> loc_write_vol_FAT_str_1:
  1154 000080D5 66B83332            <1> 	mov	ax, '32' ; FAT32
  1155 000080D9 80F902              <1> 	cmp	cl, 2 ; [esi+LD_FATType]
  1156 000080DC 7708                <1> 	ja	short loc_write_vol_FAT_str_2
  1157 000080DE 66B83132            <1> 	mov	ax, '12' ; FAT12
  1158 000080E2 7202                <1> 	jb	short loc_write_vol_FAT_str_2
  1159 000080E4 B436                <1> 	mov	ah, '6'  ; FAT16
  1160                              <1> loc_write_vol_FAT_str_2:
  1161 000080E6 C70746415420        <1> 	mov	dword [edi], 'FAT '
  1162 000080EC 66894704            <1> 	mov	word [edi+4], ax
  1163                              <1> 	;
  1164                              <1> 	;movzx	ebx, word [esi+LD_BPB+BPB_BytsPerSec]
  1165 000080F0 668B5E11            <1> 	mov	bx, [esi+LD_BPB+BPB_BytsPerSec]
  1166 000080F4 8B4674              <1> 	mov	eax, [esi+LD_FreeSectors]
  1167                              <1> 
  1168                              <1> loc_vol_freespace_recalc0:
  1169                              <1> 	; 01/03/2016
  1170 000080F7 83F8FF              <1> 	cmp	eax, 0FFFFFFFFh
  1171 000080FA 720F                <1> 	jb	short loc_vol_freespace_mul32
  1172                              <1> 	;inc	eax ; 0
  1173 000080FC 20C9                <1> 	and	cl, cl ; byte [esi+LD_FATType]
  1174 000080FE 740B                <1> 	jz	short loc_vol_freespace_mul32 	
  1175 00008100 53                  <1> 	push	ebx
  1176 00008101 66BB00FF            <1> 	mov	bx, 0FF00h ; recalculate free sectors
  1177 00008105 E876490000          <1> 	call	calculate_fat_freespace
  1178 0000810A 5B                  <1> 	pop	ebx
  1179                              <1> 
  1180                              <1> loc_vol_freespace_mul32:
  1181 0000810B F7E3                <1> 	mul	ebx
  1182 0000810D 09D2                <1> 	or	edx, edx
  1183 0000810F 7507                <1> 	jnz	short loc_vol_fspace_in_kbytes
  1184                              <1> loc_vol_fspace_in_bytes:
  1185 00008111 B9[4C140100]        <1> 	mov	ecx, VolSize_Bytes
  1186 00008116 EB0D                <1> 	jmp	short loc_write_vol_fspace_str
  1187                              <1> loc_vol_fspace_in_kbytes:
  1188 00008118 66BB0004            <1> 	mov	bx, 1024
  1189 0000811C F7F3                <1> 	div	ebx
  1190 0000811E B9[3F140100]        <1> 	mov 	ecx, VolSize_KiloBytes
  1191 00008123 31D2                <1> 	xor	edx, edx ; 0
  1192                              <1> loc_write_vol_fspace_str:
  1193 00008125 890D[7F660100]      <1> 	mov	[VolSize_Unit2], ecx
  1194                              <1> 	;	
  1195 0000812B BF[A1660100]        <1> 	mov	edi, Vol_Free_Sectors_Str_End
  1196                              <1>         ;mov	byte [edi], 0
  1197 00008130 B90A000000          <1> 	mov	ecx, 10
  1198                              <1> loc_write_vol_fspace_chr:
  1199 00008135 F7F1                <1> 	div	ecx
  1200 00008137 80C230              <1> 	add	dl, '0'
  1201 0000813A 4F                  <1> 	dec	edi	
  1202 0000813B 8817                <1> 	mov	[edi], dl
  1203 0000813D 85C0                <1> 	test	eax, eax
  1204 0000813F 7404                <1> 	jz	short loc_write_vol_fspace_str_ok
  1205 00008141 28D2                <1> 	sub	dl, dl ; 0
  1206 00008143 EBF0                <1> 	jmp	short loc_write_vol_fspace_chr
  1207                              <1> 
  1208                              <1> loc_write_vol_fspace_str_ok:
  1209 00008145 893D[93660100]      <1> 	mov	[Vol_Free_Sectors_Str_Start], edi
  1210                              <1> 	;
  1211 0000814B BE[55140100]        <1> 	mov	esi, Volume_in_drive
  1212 00008150 E8B0EAFFFF          <1> 	call	print_msg
  1213 00008155 BE[95140100]        <1> 	mov	esi, Vol_Name
  1214 0000815A E8A6EAFFFF          <1> 	call	print_msg
  1215 0000815F BE[631F0100]        <1> 	mov	esi, nextline
  1216 00008164 E89CEAFFFF          <1> 	call	print_msg
  1217                              <1> 	;
  1218 00008169 BE[F6140100]        <1> 	mov	esi, Vol_Total_Sector_Header
  1219 0000816E E892EAFFFF          <1> 	call	print_msg
  1220 00008173 8B35[83660100]      <1> 	mov	esi, [Vol_Tot_Sec_Str_Start]
  1221 00008179 E887EAFFFF          <1> 	call	print_msg
  1222 0000817E 8B35[7B660100]      <1> 	mov	esi, [VolSize_Unit1]
  1223 00008184 E87CEAFFFF          <1> 	call	print_msg
  1224                              <1> 	;
  1225 00008189 BE[07150100]        <1> 	mov	esi, Vol_Free_Sectors_Header
  1226 0000818E E872EAFFFF          <1> 	call	print_msg
  1227 00008193 8B35[93660100]      <1> 	mov	esi, [Vol_Free_Sectors_Str_Start]
  1228 00008199 E867EAFFFF          <1> 	call	print_msg
  1229 0000819E 8B35[7F660100]      <1> 	mov	esi, [VolSize_Unit2]
  1230 000081A4 E85CEAFFFF          <1> 	call	print_msg
  1231                              <1> 	;
  1232 000081A9 5E                  <1> 	pop	esi
  1233                              <1> 	
  1234                              <1> 	;mov	ah, [esi+LD_FSType]
  1235                              <1> 	;mov	al, [esi+LD_FATType]
  1236 000081AA 668B4603            <1> 	mov	ax, [esi+LD_FATType]
  1237                              <1> 
  1238 000081AE C3                  <1> 	retn
  1239                              <1> 
  1240                              <1> move_volume_name_and_serial_no:
  1241                              <1> 	; 08/02/2016  (TRDOS 386 = TRDOS v2.0)
  1242                              <1> 	; this routine will be called by
  1243                              <1> 	; "print_volume_info" and "print_directory"
  1244                              <1> 	; INPUT ->
  1245                              <1> 	;	ESI = Logical DOS drv descripton table address
  1246                              <1> 	; OUTPUT ->
  1247                              <1> 	;	*Volume name will be moved to text area
  1248                              <1> 	;	*Volume serial number will be converted to
  1249                              <1> 	;	 text and will be moved to text area
  1250                              <1> 	;   cf = 1 -> invalid/unknown dos drive
  1251                              <1> 	;   cf = 0 -> ecx = 0
  1252                              <1> 	;
  1253                              <1> 	; (eax, edx, ecx, esi, edi will be changed)
  1254                              <1> 
  1255 000081AF BF[95140100]        <1> 	mov 	edi, Vol_Name
  1256                              <1> 
  1257                              <1> 	;mov	ah, [esi+LD_FSType]
  1258                              <1> 	;mov	al, [esi+LD_FATType]
  1259 000081B4 668B4603            <1> 	mov	ax, [esi+LD_FATType]
  1260 000081B8 80FCA1              <1> 	cmp	ah, 0A1h
  1261 000081BB 7418                <1> 	je	short mvn_2
  1262 000081BD 08E4                <1> 	or	ah, ah
  1263 000081BF 7404                <1> 	jz	short mvn_0
  1264 000081C1 08C0                <1> 	or	al, al
  1265 000081C3 7504                <1> 	jnz	short mvn_1
  1266                              <1> mvn_0:
  1267 000081C5 8A06                <1> 	mov	al, [esi]
  1268 000081C7 F9                  <1> 	stc
  1269 000081C8 C3                  <1> 	retn
  1270                              <1> mvn_1:
  1271 000081C9 3C02                <1> 	cmp	al, 2
  1272 000081CB 7717                <1> 	ja	short mvn_3 
  1273                              <1> 	;or	al, al
  1274                              <1> 	;jz	short mvn_2
  1275 000081CD 8B462D              <1> 	mov	eax, [esi+LD_BPB+VolumeID]
  1276 000081D0 83C631              <1> 	add	esi, LD_BPB+VolumeLabel
  1277 000081D3 EB15                <1> 	jmp	short mvn_4
  1278                              <1> mvn_2:
  1279 000081D5 8B4628              <1> 	mov	eax, [esi+LD_FS_VolumeSerial]
  1280 000081D8 83C62C              <1> 	add	esi, LD_FS_VolumeName
  1281 000081DB B910000000          <1> 	mov	ecx, 16
  1282 000081E0 F3A5                <1> 	rep	movsd
  1283 000081E2 EB10                <1> 	jmp	short mvn_5
  1284                              <1> mvn_3:
  1285 000081E4 8B4649              <1> 	mov	eax, [esi+LD_BPB+FAT32_VolID]
  1286 000081E7 83C64D              <1> 	add	esi, LD_BPB+FAT32_VolLab
  1287                              <1> mvn_4:
  1288 000081EA B90B000000          <1> 	mov	ecx, 11
  1289 000081EF F3A4                <1> 	rep	movsb
  1290 000081F1 C60700              <1> 	mov	byte [edi], 0
  1291                              <1> mvn_5:
  1292                              <1> 	;mov	[Current_VolSerial], eax  
  1293 000081F4 E827B8FFFF          <1> 	call	dwordtohex
  1294 000081F9 8915[EA140100]      <1> 	mov	[Vol_Serial1], edx
  1295 000081FF A3[EF140100]        <1> 	mov	[Vol_Serial2], eax
  1296                              <1> 	; ecx = 0
  1297 00008204 C3                  <1> 	retn
  1298                              <1> 
  1299                              <1> get_volume_serial_number:
  1300                              <1> 	; 19/01/2016 (TRDOS 386 = TRDOS v2.0)
  1301                              <1> 	; 08/08/2010
  1302                              <1> 	;
  1303                              <1> 	; INPUT -> DL = Logical DOS Drive number
  1304                              <1> 	; OUTPUT -> EAX = Volume serial number
  1305                              <1> 	;          BL= FAT Type	    
  1306                              <1> 	;          BH = Logical DOS drv Number (DL input)
  1307                              <1> 	; cf = 1 -> Drive not ready
  1308                              <1> 
  1309 00008205 31DB                <1> 	xor	ebx, ebx
  1310 00008207 88D7                <1> 	mov	bh, dl
  1311 00008209 3815[C6120100]      <1> 	cmp	[Last_DOS_DiskNo], dl
  1312 0000820F 7304                <1> 	jnb	short loc_gvsn_start
  1313                              <1> loc_gvsn_stc_retn:
  1314 00008211 31C0                <1> 	xor	eax, eax
  1315 00008213 F9                  <1> 	stc 
  1316 00008214 C3                  <1>         retn 
  1317                              <1> loc_gvsn_start:
  1318 00008215 56                  <1> 	push	esi
  1319 00008216 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  1320 0000821B 01DE                <1> 	add	esi, ebx
  1321 0000821D 8A5E03              <1> 	mov	bl, [esi+LD_FATType]
  1322 00008220 20DB                <1> 	and	bl, bl
  1323 00008222 740F                <1> 	jz	short loc_gvsn_fs
  1324 00008224 80FB02              <1> 	cmp	bl, 2
  1325 00008227 7705                <1> 	ja	short loc_gvsn_fat32
  1326                              <1> loc_gvsn_fat:
  1327 00008229 83C62D              <1> 	add	esi, LD_BPB + VolumeID
  1328 0000822C EB0E                <1> 	jmp	short loc_gvsn_return
  1329                              <1> loc_gvsn_fat32: 
  1330 0000822E 83C649              <1> 	add	esi, LD_BPB + FAT32_VolID
  1331 00008231 EB09                <1> 	jmp	short loc_gvsn_return 
  1332                              <1> loc_gvsn_fs:
  1333 00008233 807E04A1            <1> 	cmp	byte [esi+LD_FSType], 0A1h
  1334 00008237 75D8                <1> 	jne	short loc_gvsn_stc_retn 
  1335 00008239 83C628              <1> 	add	esi, LD_FS_VolumeSerial
  1336                              <1> loc_gvsn_return:
  1337 0000823C 8B06                <1> 	mov	eax, [esi]
  1338 0000823E 5E                  <1> 	pop	esi
  1339 0000823F C3                  <1> 	retn
  1340                              <1> 
  1341                              <1> ; CMD_INTR.ASM [ TRDOS Command Interpreter Procedure ]
  1342                              <1> ; 09/11/2011
  1343                              <1> ; 29/01/2005
  1344                              <1> 
  1345                              <1> command_interpreter:
  1346                              <1> 	; 16/10/2016
  1347                              <1> 	; 12/10/2016
  1348                              <1> 	; 13/05/2016
  1349                              <1> 	; 07/05/2016
  1350                              <1> 	; 04/03/2016
  1351                              <1> 	; 04/02/2016
  1352                              <1> 	; 03/02/2016
  1353                              <1> 	; 30/01/2016
  1354                              <1> 	; 29/01/2016 (TRDOS 386 = TRDOS 2.0)
  1355                              <1> 	; 15/09/2011         
  1356                              <1> 	; 29/01/2005
  1357                              <1>         
  1358                              <1> 	; Input: ecx = command word length (CL)
  1359                              <1> 	;	 CommandBuffer = Command string offset
  1360                              <1>  
  1361 00008240 C605[34670100]00    <1> 	mov	byte [Program_Exit],0
  1362 00008247 80F904              <1> 	cmp	cl, 4
  1363 0000824A 0F87B5020000        <1>         ja      c_6
  1364 00008250 0F8237010000        <1>         jb      c_2
  1365                              <1> c_4:
  1366                              <1> 
  1367                              <1> cmp_cmd_exit:
  1368 00008256 BF[34130100]        <1> 	mov	edi, Cmd_Exit
  1369 0000825B E8C2030000          <1> 	call	cmp_cmd	
  1370 00008260 7208                <1> 	jc	short cmp_cmd_date
  1371                              <1> 
  1372 00008262 C605[34670100]01    <1>         mov     byte [Program_Exit], 1
  1373 00008269 C3                  <1>         retn
  1374                              <1> 
  1375                              <1> cmp_cmd_date:
  1376 0000826A B104                <1> 	mov	cl, 4
  1377 0000826C BF[50130100]        <1> 	mov	edi, Cmd_Date
  1378 00008271 E8AC030000          <1> 	call	cmp_cmd	
  1379 00008276 720B                <1>         jc	short cmp_cmd_time
  1380                              <1> 	
  1381 00008278 E8D0F7FFFF          <1> 	call	show_date
  1382 0000827D E80FF8FFFF          <1> 	call	set_date
  1383 00008282 C3                  <1> 	retn
  1384                              <1> 
  1385                              <1> cmp_cmd_time:
  1386 00008283 B104                <1> 	mov	cl, 4
  1387 00008285 BF[55130100]        <1> 	mov	edi, Cmd_Time
  1388 0000828A E893030000          <1>    	call	cmp_cmd	
  1389 0000828F 720B                <1> 	jc	short cmp_cmd_show
  1390                              <1> 
  1391 00008291 E8C6FAFFFF          <1> 	call	show_time
  1392 00008296 E8F8FAFFFF          <1> 	call	set_time
  1393 0000829B C3                  <1> 	retn
  1394                              <1> 
  1395                              <1> cmp_cmd_show:
  1396 0000829C B104                <1> 	mov	cl, 4
  1397 0000829E BF[66130100]        <1> 	mov	edi, Cmd_Show
  1398 000082A3 E87A030000          <1>    	call	cmp_cmd	
  1399 000082A8 0F83050A0000        <1>         jnc     show_file
  1400                              <1> 
  1401                              <1> cmp_cmd_echo:
  1402 000082AE B104                <1> 	mov	cl, 4
  1403 000082B0 BF[A2130100]        <1> 	mov	edi, Cmd_Echo
  1404 000082B5 E868030000          <1>    	call	cmp_cmd	
  1405 000082BA 7224                <1> 	jc	short cmp_cmd_copy
  1406                              <1> 	
  1407                              <1> 	; 22/11/2017
  1408                              <1> 	; AL = 0
  1409 000082BC 803E20              <1> 	cmp	byte [esi], 20h
  1410 000082BF 7215                <1> 	jb	short cmd_echo_nextline
  1411                              <1> 	; 14/04/2016
  1412 000082C1 56                  <1> 	push	esi
  1413                              <1> cmd_echo_asciiz:
  1414                              <1> 	;inc	esi
  1415                              <1> 	;mov	al, [esi]
  1416                              <1> 	; 22/11/2017
  1417 000082C2 AC                  <1> 	lodsb
  1418 000082C3 3C20                <1> 	cmp	al, 20h
  1419 000082C5 73FB                <1> 	jnb	short cmd_echo_asciiz
  1420 000082C7 4E                  <1> 	dec	esi
  1421 000082C8 C60600              <1> 	mov	byte [esi], 0
  1422 000082CB 5E                  <1> 	pop	esi
  1423 000082CC 89F7                <1> 	mov	edi, esi
  1424 000082CE E832E9FFFF          <1> 	call	print_msg
  1425 000082D3 C60700              <1> 	mov	byte [edi], 0	
  1426                              <1> cmd_echo_nextline:
  1427 000082D6 BE[AC1F0100]        <1> 	mov	esi, NextLine
  1428                              <1> 	;call	print_msg   
  1429                              <1> 	;retn
  1430 000082DB E925E9FFFF          <1> 	jmp	print_msg
  1431                              <1> 
  1432                              <1> cmp_cmd_copy:
  1433 000082E0 B104                <1> 	mov	cl, 4
  1434 000082E2 BF[89130100]        <1> 	mov	edi, Cmd_Copy
  1435 000082E7 E836030000          <1>    	call	cmp_cmd	
  1436 000082EC 0F83CC170000        <1> 	jnc	copy_file
  1437                              <1> 
  1438                              <1> cmp_cmd_move:
  1439 000082F2 B104                <1> 	mov	cl, 4
  1440 000082F4 BF[8E130100]        <1> 	mov	edi, Cmd_Move
  1441 000082F9 E824030000          <1>    	call	cmp_cmd	
  1442 000082FE 0F836E160000        <1> 	jnc	move_file
  1443                              <1> 
  1444                              <1> cmp_cmd_path:
  1445 00008304 B104                <1> 	mov	cl, 4
  1446 00008306 BF[93130100]        <1> 	mov	edi, Cmd_Path
  1447 0000830B E812030000          <1>    	call	cmp_cmd	
  1448 00008310 0F83F0190000        <1> 	jnc	set_get_path
  1449                              <1> 
  1450                              <1> cmp_cmd_beep:
  1451 00008316 B104                <1> 	mov	cl, 4
  1452 00008318 BF[C0130100]        <1> 	mov	edi, Cmd_Beep
  1453 0000831D E800030000          <1>    	call	cmp_cmd	
  1454 00008322 720B                <1> 	jc	short cmp_cmd_find
  1455                              <1> 	; 13/05/2016
  1456 00008324 8A3D[AE5E0100]      <1> 	mov	bh, [ptty] ; [ACTIVE_PAGE]
  1457 0000832A E98E9EFFFF          <1> 	jmp	beeper
  1458                              <1> 
  1459                              <1> cmp_cmd_find:
  1460 0000832F B104                <1> 	mov	cl, 4
  1461 00008331 BF[9D130100]        <1> 	mov	edi, Cmd_Find
  1462 00008336 E8E7020000          <1>    	call	cmp_cmd	
  1463 0000833B 0F82C4020000        <1>         jc      cmp_cmd_external
  1464                              <1> 
  1465                              <1> 	;call	find_and_list_files
  1466 00008341 E9AF220000          <1> 	jmp	find_and_list_files
  1467                              <1> 	;retn
  1468                              <1> 
  1469                              <1> c_1:
  1470 00008346 AD                  <1> 	lodsd
  1471                              <1> cmp_cmd_help:
  1472 00008347 3C3F                <1> 	cmp	al, '?'
  1473 00008349 751D                <1>         jne     short cmp_cmd_remark
  1474                              <1> 
  1475 0000834B BE[26130100]        <1> 	mov	esi, Command_List
  1476                              <1> cmd_help_next_w:
  1477 00008350 E8B0E8FFFF          <1> 	call	print_msg
  1478                              <1> 
  1479 00008355 803E20              <1> 	cmp	byte [esi], 20h ; 0
  1480 00008358 7232                <1> 	jb	short cmd_help_retn
  1481                              <1> 	
  1482 0000835A 56                  <1> 	push	esi
  1483 0000835B BE[631F0100]        <1> 	mov	esi, nextline
  1484 00008360 E8A0E8FFFF          <1> 	call	print_msg
  1485 00008365 5E                  <1> 	pop	esi
  1486 00008366 EBE8                <1> 	jmp	short cmd_help_next_w	
  1487                              <1> 
  1488                              <1> cmp_cmd_remark:
  1489 00008368 3C2A                <1> 	cmp	al, '*'
  1490 0000836A 0F8595020000        <1>         jne     cmp_cmd_external
  1491 00008370 46                  <1> 	inc	esi
  1492 00008371 BF[A85F0100]        <1> 	mov	edi, Remark
  1493 00008376 8A06                <1> 	mov	al, [esi]
  1494 00008378 3C20                <1> 	cmp	al, 20h
  1495 0000837A 7707                <1> 	ja	short cmd_remark_write
  1496 0000837C 89FE                <1> 	mov	esi, edi ; Remark
  1497 0000837E E982E8FFFF          <1> 	jmp	print_msg
  1498                              <1> 
  1499                              <1> cmd_remark_write:
  1500 00008383 AA                  <1> 	stosb
  1501 00008384 AC                  <1> 	lodsb
  1502 00008385 3C20                <1> 	cmp	al, 20h
  1503 00008387 73FA                <1> 	jnb	short cmd_remark_write
  1504 00008389 C60700              <1> 	mov	byte [edi], 0
  1505                              <1> 
  1506                              <1> cmd_help_retn:
  1507                              <1> cmd_remark_retn:
  1508                              <1> cd_retn:
  1509 0000838C C3                  <1> 	retn
  1510                              <1> 
  1511                              <1> c_2:
  1512 0000838D 80F902              <1> 	cmp	cl, 2
  1513 00008390 0F87AF000000        <1>         ja      c_3
  1514 00008396 BE[F65F0100]        <1> 	mov	esi, CommandBuffer
  1515 0000839B 72A9                <1> 	jb	short c_1
  1516                              <1> 
  1517                              <1> cmp_cmd_cd:
  1518 0000839D 66AD                <1> 	lodsw
  1519 0000839F 663D4344            <1> 	cmp	ax, 'CD'
  1520 000083A3 7551                <1> 	jne	short cmp_cmd_drive
  1521 000083A5 46                  <1>         inc	esi
  1522                              <1> cd_0:
  1523 000083A6 668B06              <1> 	mov	ax, [esi]	
  1524 000083A9 3C20                <1> 	cmp	al, 20h
  1525 000083AB 76DF                <1> 	jna	short cd_retn
  1526                              <1> 	; 10/02/2016
  1527 000083AD 80FC3A              <1> 	cmp	ah, ':'
  1528 000083B0 7504                <1> 	jne	short cd_1
  1529 000083B2 46                  <1> 	inc	esi
  1530 000083B3 46                  <1> 	inc	esi
  1531 000083B4 EB49                <1> 	jmp	short cd_2
  1532                              <1> 
  1533                              <1> cd_1:	; change current directory
  1534                              <1> 	; 29/11/2009
  1535                              <1> 	; AH = CDh	; to separate 'CD' command from others
  1536                              <1> 			; for restoring current directory
  1537                              <1> 			; 0CDh sign is for saving cdir into 
  1538                              <1> 			; DOS drv description table cdir area
  1539                              <1> 	
  1540 000083B6 B4CD                <1> 	mov	ah, 0CDh ; mov byte [CD_COMMAND], 0CDh 
  1541                              <1> 
  1542 000083B8 E81D230000          <1> 	call	change_current_directory
  1543 000083BD 0F8337220000        <1>         jnc     change_prompt_dir_string
  1544                              <1> 
  1545                              <1> cd_error_messages:
  1546 000083C3 3C03                <1> 	cmp	al, 3
  1547 000083C5 740C                <1> 	je	short cd_path_not_found
  1548                              <1> 	; 16/10/2016 (15h -> 15)
  1549 000083C7 3C0F                <1> 	cmp	al, 15 ; drive not ready error 
  1550 000083C9 7459                <1> 	je	short cd_drive_not_ready
  1551 000083CB 3C11                <1> 	cmp	al, 17 ; read error
  1552 000083CD 7455                <1> 	je	short cd_drive_not_ready	
  1553 000083CF 3C13                <1> 	cmp	al, 19 ; ; Bad directory/path name 
  1554 000083D1 7466                <1> 	je	short cd_command_failed
  1555                              <1> 
  1556                              <1> cd_path_not_found:
  1557 000083D3 50                  <1> 	push	eax ; 29/12/2017
  1558                              <1> 	;push	ax	
  1559 000083D4 BE[C9150100]        <1> 	mov	esi, Msg_Dir_Not_Found
  1560 000083D9 E827E8FFFF          <1> 	call	print_msg
  1561                              <1> 	;pop	ax
  1562 000083DE 58                  <1> 	pop	eax ; 29/12/2017
  1563 000083DF 3A25[445F0100]      <1> 	cmp	ah, [Current_Dir_Level]
  1564 000083E5 0F830F220000        <1>         jnb     change_prompt_dir_string
  1565 000083EB 8825[445F0100]      <1> 	mov	[Current_Dir_Level], ah
  1566 000083F1 E904220000          <1>         jmp     change_prompt_dir_string   
  1567                              <1> 
  1568                              <1> cmp_cmd_drive: ; change current drive
  1569                              <1> 	; C:, D:, E: etc.
  1570 000083F6 80FC3A              <1> 	cmp	ah, ':'
  1571 000083F9 0F8506020000        <1>         jne     cmp_cmd_external
  1572                              <1> 
  1573                              <1> cd_2:	; 'CD C:', 'CD D:' ...
  1574 000083FF 803E20              <1> 	cmp	byte [esi], 20h
  1575 00008402 0F8707020000        <1>         ja      loc_cmd_failed
  1576                              <1> 
  1577 00008408 24DF                <1> 	and	al, 0DFh
  1578 0000840A 2C41                <1> 	sub	al, 'A'
  1579 0000840C 0F82FD010000        <1>         jc      loc_cmd_failed
  1580                              <1> 
  1581 00008412 3A05[C6120100]      <1>         cmp     al, [Last_DOS_DiskNo]
  1582 00008418 770A                <1>         ja	short cd_drive_not_ready
  1583                              <1> 	
  1584 0000841A 88C2                <1> 	mov	dl, al
  1585 0000841C E85BF3FFFF          <1> 	call 	change_current_drive
  1586 00008421 7201                <1> 	jc	short cd_drive_not_ready	
  1587 00008423 C3                  <1> 	retn
  1588                              <1> 
  1589                              <1> cd_drive_not_ready:
  1590 00008424 BE[86150100]        <1> 	mov	esi, Msg_Not_Ready_Read_Err
  1591 00008429 E8D7E7FFFF          <1> 	call	print_msg
  1592                              <1> 
  1593                              <1> cd_fail_drive_restart:
  1594 0000842E 8A15[465F0100]      <1> 	mov	dl, [Current_Drv]
  1595                              <1> 	;call 	change_current_drive
  1596 00008434 E943F3FFFF          <1>         jmp     change_current_drive
  1597                              <1> 	;retn
  1598                              <1> 
  1599                              <1> cd_command_failed:
  1600 00008439 BE[67150100]        <1> 	mov	esi, Msg_Bad_Command
  1601 0000843E E8C2E7FFFF          <1> 	call	print_msg
  1602 00008443 EBE9                <1> 	jmp	short cd_fail_drive_restart
  1603                              <1> 
  1604                              <1> c_3:
  1605                              <1> cmp_cmd_dir:
  1606 00008445 BF[26130100]        <1> 	mov	edi, Cmd_Dir
  1607 0000844A E8D3010000          <1> 	call	cmp_cmd	
  1608 0000844F 0F8380020000        <1> 	jnc	print_directory_list
  1609                              <1> 
  1610                              <1> cmp_cmd_cls:
  1611 00008455 B103                <1> 	mov	cl, 3
  1612 00008457 BF[62130100]        <1> 	mov	edi, Cmd_Cls
  1613 0000845C E8C1010000          <1> 	call	cmp_cmd	
  1614 00008461 0F83B4E7FFFF        <1>         jnc	clear_screen
  1615                              <1> 
  1616                              <1> cmp_cmd_ver:
  1617 00008467 B103                <1> 	mov	cl, 3
  1618 00008469 BF[30130100]        <1> 	mov	edi, Cmd_Ver
  1619 0000846E E8AF010000          <1> 	call	cmp_cmd	
  1620 00008473 720A                <1> 	jc	short cmp_cmd_mem
  1621                              <1> 
  1622 00008475 BE[CE120100]        <1> 	mov	esi, mainprog_Version
  1623                              <1> 	;call	print_msg
  1624 0000847A E986E7FFFF          <1> 	jmp	print_msg
  1625                              <1> 	;retn
  1626                              <1> 
  1627                              <1> cmp_cmd_mem:
  1628 0000847F B103                <1> 	mov	cl, 3
  1629 00008481 BF[98130100]        <1> 	mov	edi, Cmd_Mem
  1630 00008486 E897010000          <1> 	call	cmp_cmd	
  1631 0000848B 0F83DAB4FFFF        <1> 	jnc	memory_info
  1632                              <1> 
  1633                              <1> cmp_cmd_del:
  1634 00008491 B103                <1> 	mov	cl, 3
  1635 00008493 BF[6B130100]        <1> 	mov	edi, Cmd_Del
  1636 00008498 E885010000          <1> 	call	cmp_cmd	
  1637 0000849D 0F83280F0000        <1>         jnc     delete_file
  1638                              <1> 
  1639                              <1> cmp_cmd_set:
  1640 000084A3 B103                <1> 	mov	cl, 3
  1641 000084A5 BF[5E130100]        <1> 	mov	edi, Cmd_Set
  1642 000084AA E873010000          <1> 	call	cmp_cmd	
  1643 000084AF 0F83C9170000        <1>         jnc     set_get_env
  1644                              <1> 
  1645                              <1> cmp_cmd_run:
  1646 000084B5 B103                <1> 	mov	cl, 3
  1647 000084B7 BF[5A130100]        <1> 	mov	edi, Cmd_Run
  1648 000084BC E861010000          <1> 	call	cmp_cmd	
  1649                              <1> 	; 07/05/2016
  1650 000084C1 0F823E010000        <1>         jc      cmp_cmd_external
  1651 000084C7 E90F1E0000          <1> 	jmp	load_and_execute_file
  1652                              <1> c_5:
  1653                              <1> cmp_cmd_mkdir:
  1654 000084CC BF[83130100]        <1> 	mov	edi, Cmd_Mkdir
  1655 000084D1 E84C010000          <1> 	call	cmp_cmd	
  1656 000084D6 0F83990A0000        <1>         jnc     make_directory
  1657                              <1> 
  1658                              <1> cmp_cmd_rmdir:
  1659 000084DC B105                <1> 	mov	cl, 5
  1660 000084DE BF[7D130100]        <1> 	mov	edi, Cmd_Rmdir
  1661 000084E3 E83A010000          <1> 	call	cmp_cmd	
  1662 000084E8 0F83AA0B0000        <1>         jnc     delete_directory
  1663                              <1> 
  1664                              <1> cmp_cmd_chdir:
  1665 000084EE B105                <1> 	mov	cl, 5
  1666 000084F0 BF[BA130100]        <1> 	mov	edi, Cmd_Chdir
  1667 000084F5 E828010000          <1> 	call	cmp_cmd	
  1668 000084FA 0F8205010000        <1>         jc      cmp_cmd_external
  1669                              <1> 
  1670 00008500 E9A1FEFFFF          <1> 	jmp	cd_0
  1671                              <1> 
  1672                              <1> c_6:
  1673 00008505 80F906              <1> 	cmp	cl, 6
  1674 00008508 0F87E0000000        <1>         ja      c_8
  1675 0000850E 72BC                <1> 	jb	short c_5
  1676                              <1> cmp_cmd_prompt:
  1677 00008510 BF[39130100]        <1> 	mov	edi, Cmd_Prompt
  1678 00008515 E808010000          <1> 	call	cmp_cmd	
  1679 0000851A 722F                <1>         jc	short cmp_cmd_volume
  1680                              <1> get_prompt_name_fchar:
  1681 0000851C AC                  <1> 	lodsb
  1682 0000851D 3C20                <1> 	cmp	al, 20h
  1683 0000851F 74FB                <1> 	je	short get_prompt_name_fchar
  1684 00008521 7713                <1> 	ja	short loc_change_prompt_label
  1685                              <1> default_command_prompt: ; 31/12/2017 ('sysprompt')
  1686 00008523 BE[1A130100]        <1> 	mov	esi, TRDOSPromptLabel
  1687 00008528 C7065452444F        <1> 	mov	dword [esi], "TRDO"
  1688 0000852E 66C746045300        <1>        	mov	word [esi+4], "S" 
  1689                              <1> loc_cmd_prompt_return:
  1690 00008534 C3                  <1> 	retn
  1691                              <1> 
  1692                              <1> set_command_prompt: ; 31/12/2017 ('sysprompt')
  1693 00008535 AC                  <1> 	lodsb
  1694                              <1> loc_change_prompt_label:
  1695 00008536 66B90B00            <1> 	mov	cx, 11
  1696 0000853A BF[1A130100]        <1> 	mov	edi, TRDOSPromptLabel
  1697                              <1> put_char_new_prompt_label:
  1698 0000853F AA                  <1> 	stosb
  1699 00008540 AC                  <1> 	lodsb
  1700 00008541 3C20                <1> 	cmp	al, 20h
  1701 00008543 7202                <1> 	jb	short pass_put_new_prompt_label
  1702 00008545 E2F8                <1> 	loop	put_char_new_prompt_label
  1703                              <1> pass_put_new_prompt_label:
  1704 00008547 C60700              <1> 	mov	byte [edi], 0
  1705 0000854A C3                  <1> 	retn
  1706                              <1> 
  1707                              <1> cmp_cmd_volume:
  1708 0000854B B106                <1> 	mov	cl, 6
  1709 0000854D BF[40130100]        <1> 	mov	edi, Cmd_Volume
  1710 00008552 E8CB000000          <1> 	call	cmp_cmd	
  1711 00008557 7255                <1>         jc	short cmp_cmd_attrib
  1712                              <1> 
  1713                              <1> cmd_vol1:
  1714 00008559 AC                  <1> 	lodsb
  1715 0000855A 3C20                <1> 	cmp	al, 20h
  1716 0000855C 7707                <1> 	ja	short cmd_vol2
  1717 0000855E A0[465F0100]        <1> 	mov	al, [Current_Drv]
  1718 00008563 EB3D                <1> 	jmp	short cmd_vol4
  1719                              <1> cmd_vol2:
  1720 00008565 3C41                <1> 	cmp	al, 'A'
  1721 00008567 0F82A2000000        <1>         jb      loc_cmd_failed
  1722 0000856D 3C7A                <1> 	cmp	al, 'z'
  1723 0000856F 0F879A000000        <1>         ja      loc_cmd_failed
  1724 00008575 3C5A                <1> 	cmp	al, 'Z'
  1725 00008577 760A                <1> 	jna	short cmd_vol3
  1726 00008579 3C61                <1> 	cmp	al, 'a'
  1727 0000857B 0F828E000000        <1>         jb      loc_cmd_failed
  1728 00008581 24DF                <1> 	and	al, 0DFh
  1729                              <1> cmd_vol3:
  1730 00008583 8A26                <1> 	mov	ah, [esi]
  1731 00008585 80FC3A              <1> 	cmp	ah, ':'
  1732 00008588 0F8581000000        <1>         jne     loc_cmd_failed
  1733 0000858E 2C41                <1> 	sub	al, 'A'
  1734 00008590 3A05[C6120100]      <1>         cmp     al, [Last_DOS_DiskNo]
  1735 00008596 760A                <1> 	jna	short cmd_vol4
  1736                              <1> 
  1737 00008598 BE[86150100]        <1> 	mov	esi, Msg_Not_Ready_Read_Err
  1738 0000859D E963E6FFFF          <1> 	jmp	print_msg
  1739                              <1> 	
  1740                              <1> cmd_vol4:
  1741 000085A2 E88EFAFFFF          <1> 	call	print_volume_info
  1742 000085A7 0F8277FEFFFF        <1>         jc      cd_drive_not_ready
  1743 000085AD C3                  <1> 	retn
  1744                              <1> 
  1745                              <1> cmp_cmd_attrib:
  1746 000085AE B106                <1> 	mov	cl, 6
  1747 000085B0 BF[6F130100]        <1> 	mov	edi, Cmd_Attrib
  1748 000085B5 E868000000          <1> 	call	cmp_cmd	
  1749 000085BA 0F831D0F0000        <1>         jnc     set_file_attributes
  1750                              <1> 
  1751                              <1> cmp_cmd_rename:
  1752 000085C0 B106                <1> 	mov	cl, 6
  1753 000085C2 BF[76130100]        <1> 	mov	edi, Cmd_Rename
  1754 000085C7 E856000000          <1> 	call	cmp_cmd	
  1755 000085CC 0F8353110000        <1>         jnc     rename_file
  1756                              <1> 
  1757                              <1> cmp_cmd_device:
  1758 000085D2 B106                <1> 	mov	cl, 6
  1759 000085D4 BF[AB130100]        <1> 	mov	edi, Cmd_Device
  1760 000085D9 E844000000          <1> 	call	cmp_cmd	
  1761 000085DE 7225                <1>         jc	short cmp_cmd_external
  1762                              <1> 
  1763 000085E0 C3                  <1> 	retn
  1764                              <1> 
  1765                              <1> c_7:
  1766                              <1> cmp_cmd_devlist:
  1767 000085E1 BF[B2130100]        <1> 	mov	edi, Cmd_DevList
  1768 000085E6 E837000000          <1> 	call	cmp_cmd	
  1769 000085EB 7218                <1>         jc	short cmp_cmd_external
  1770                              <1> 
  1771                              <1> loc_cmd_return:
  1772 000085ED C3                  <1> 	retn
  1773                              <1> 
  1774                              <1> c_8:
  1775 000085EE 80F908              <1>         cmp	cl, 8
  1776 000085F1 7712                <1> 	ja	short cmp_cmd_external
  1777 000085F3 72EC                <1> 	jb	short c_7
  1778                              <1> 
  1779                              <1> cmp_cmd_longname:
  1780 000085F5 BF[47130100]        <1> 	mov	edi, Cmd_LongName
  1781 000085FA E823000000          <1> 	call	cmp_cmd	
  1782 000085FF 0F8350060000        <1>         jnc     get_and_print_longname
  1783                              <1> 
  1784                              <1> cmp_cmd_external:
  1785                              <1> 	; 07/05/2016
  1786                              <1> 	; 22/04/2016
  1787 00008605 BE[F65F0100]        <1> 	mov	esi, CommandBuffer
  1788 0000860A E9CC1C0000          <1> 	jmp	loc_run_check_filename 
  1789                              <1> 
  1790                              <1> loc_cmd_failed:
  1791 0000860F 803D[F65F0100]20    <1> 	cmp	byte [CommandBuffer], 20h
  1792 00008616 76D5                <1> 	jna	short loc_cmd_return
  1793 00008618 BE[67150100]        <1> 	mov	esi, Msg_Bad_Command
  1794                              <1> ;	call	print_msg
  1795                              <1> ;loc_cmd_return:
  1796                              <1> ;	retn
  1797 0000861D E9E3E5FFFF          <1> 	jmp	print_msg
  1798                              <1> 
  1799                              <1> cmp_cmd:
  1800                              <1> 	 ; 29/01/2016 (TRDOS 386 = TRDOS v2.0)
  1801 00008622 BE[F65F0100]        <1>          mov	esi, CommandBuffer
  1802                              <1>          ; edi = internal command word (ASCIIZ)
  1803                              <1> 	 ; ecx = command length (<=8)
  1804                              <1> cmp_cmd_1:
  1805 00008627 AC                  <1> 	lodsb
  1806 00008628 AE                  <1> 	scasb
  1807 00008629 750D                <1> 	jne	short cmp_cmd_3
  1808 0000862B E2FA                <1> 	loop	cmp_cmd_1
  1809 0000862D AC                  <1>  	lodsb
  1810 0000862E 3C20                <1> 	cmp	al, 20h
  1811 00008630 7703                <1> 	ja	short cmp_cmd_2
  1812 00008632 30C0                <1> 	xor	al, al
  1813                              <1> 	; ZF = 1 -> internal command word matches
  1814 00008634 C3                  <1> 	retn
  1815                              <1> cmp_cmd_2:
  1816                              <1> 	; ZF = 0 (CF = 0) -> external command word 	
  1817 00008635 58                  <1> 	pop	eax ; no return to the caller from here 
  1818 00008636 EBCD                <1> 	jmp	cmp_cmd_external	
  1819                              <1> cmp_cmd_3:
  1820 00008638 F9                  <1> 	stc
  1821                              <1> 	; CF = 1 -> internal command word does not match
  1822 00008639 C3                  <1> 	retn
  1823                              <1> 
  1824                              <1> loc_run_cmd_failed:
  1825                              <1> 	; 15/03/2016
  1826                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  1827                              <1> 	; 07/12/2009 (CMD_INTR.ASM)	
  1828                              <1> 	; 29/11/2009
  1829                              <1> 
  1830 0000863A E863000000          <1> 	call	restore_cdir_after_cmd_fail
  1831                              <1> 
  1832                              <1> loc_run_cmd_failed_cmp_al:
  1833                              <1> 	; End of Restore_CDIR code (29/11/2009)
  1834                              <1> 
  1835 0000863F 3C01                <1> 	cmp	al, 1 ; Bad command or file name
  1836 00008641 74CC                <1> 	je	loc_cmd_failed
  1837                              <1> loc_run_dir_not_found:
  1838 00008643 3C03                <1> 	cmp	al, 3
  1839 00008645 750A                <1> 	jne	short loc_run_file_notfound_msg
  1840                              <1> 	; Path not found (MS-DOS Error Code = 3)
  1841 00008647 BE[C9150100]        <1> 	mov	esi, Msg_Dir_Not_Found
  1842 0000864C E9B4E5FFFF          <1> 	jmp	print_msg
  1843                              <1> 
  1844                              <1> loc_run_file_notfound_msg:
  1845 00008651 3C02                <1> 	cmp	al, 2 ; File not found
  1846 00008653 750A                <1> 	jne	short loc_run_file_drv_read_err
  1847                              <1> 
  1848                              <1> loc_print_file_notfound_msg: 
  1849 00008655 BE[E0150100]        <1>         mov     esi, Msg_File_Not_Found
  1850                              <1> 	;call	proc_printmsg
  1851                              <1> 	;retn
  1852 0000865A E9A6E5FFFF          <1> 	jmp	print_msg
  1853                              <1> 
  1854                              <1> loc_run_file_drv_read_err:
  1855                              <1> 	; Err: 17 (Read fault)
  1856 0000865F 3C11                <1> 	cmp	al, 17 ; Drive not ready or read error
  1857 00008661 7404                <1> 	je	short loc_run_file_print_drv_read_err
  1858                              <1> 	;
  1859 00008663 3C0F                <1> 	cmp	al, 15 ; Drive not ready (or read error)
  1860 00008665 750A                <1> 	jne	short loc_run_file_toobig
  1861                              <1> 
  1862                              <1> loc_run_file_print_drv_read_err:
  1863 00008667 BE[86150100]        <1> 	mov	esi, Msg_Not_Ready_Read_Err
  1864 0000866C E994E5FFFF          <1> 	jmp	print_msg
  1865                              <1> 
  1866                              <1> loc_run_file_toobig:
  1867 00008671 3C08                <1> 	cmp	al, 8 ; Not enough free memory to load&run file
  1868 00008673 750A                <1> 	jne	short loc_run_file_perm_denied
  1869 00008675 BE[2B160100]        <1> 	mov	esi, Msg_Insufficient_Memory
  1870 0000867A E986E5FFFF          <1> 	jmp	print_msg
  1871                              <1> 
  1872                              <1> loc_run_file_perm_denied:
  1873                              <1> 	; 29/12/2017
  1874 0000867F 3C0B                <1> 	cmp	al, ERR_PERM_DENIED ; 11 ; Permission denied
  1875 00008681 750A                <1> 	jne	short loc_run_misc_error
  1876 00008683 BE[C0170100]        <1> 	mov	esi, Msg_Permission_Denied
  1877 00008688 E978E5FFFF          <1> 	jmp	print_msg	
  1878                              <1> 
  1879                              <1> 	; 15/03/2016
  1880                              <1> print_misc_error_msg:
  1881                              <1> loc_run_misc_error:
  1882                              <1> 	; AL = Error code
  1883 0000868D E84EB3FFFF          <1> 	call	bytetohex
  1884 00008692 66A3[5F160100]      <1>         mov     [error_code_hex], ax
  1885                              <1> 	
  1886 00008698 BE[42160100]        <1> 	mov	esi, Msg_Error_Code 
  1887                              <1> 	;call	print_msg 
  1888                              <1> 	;retn
  1889                              <1> 
  1890 0000869D E963E5FFFF          <1> 	jmp	print_msg
  1891                              <1> 
  1892                              <1> restore_cdir_after_cmd_fail:
  1893                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  1894 000086A2 50                  <1> 	push	eax
  1895 000086A3 8A3D[A2660100]      <1> 	mov	bh, [RUN_CDRV] ; it is set at the beginning
  1896                              <1> 				; of the 'run' command.
  1897 000086A9 3A3D[465F0100]      <1> 	cmp	bh, [Current_Drv]
  1898 000086AF 7409                <1> 	je	short loc_run_restore_cdir
  1899 000086B1 88FA                <1> 	mov	dl, bh
  1900 000086B3 E8C4F0FFFF          <1> 	call	change_current_drive 
  1901 000086B8 EB19                <1> 	jmp	short loc_run_err_pass_restore_cdir
  1902                              <1> 
  1903                              <1> loc_run_restore_cdir:
  1904 000086BA 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  1905 000086C1 7610                <1> 	jna	short loc_run_err_pass_restore_cdir
  1906 000086C3 30DB                <1> 	xor	bl, bl
  1907 000086C5 0FB7F3              <1> 	movzx	esi, bx
  1908 000086C8 81C600010900        <1> 	add	esi, Logical_DOSDisks
  1909 000086CE E860F1FFFF          <1> 	call	restore_current_directory
  1910                              <1> 
  1911                              <1> loc_run_err_pass_restore_cdir:
  1912 000086D3 58                  <1> 	pop	eax
  1913 000086D4 C3                  <1> 	retn
  1914                              <1> 
  1915                              <1> print_directory_list:
  1916                              <1> 	; 10/02/2016
  1917                              <1> 	; 08/02/2016 (TRDOS 386 = TRDOS v2.0)
  1918                              <1> 	; 06/12/2009 ('cmp_cmd_dir')	
  1919                              <1> 	;
  1920 000086D5 66C705[E4670100]00- <1> 	mov	word [AttributesMask], 0800h ; ..except volume names..
  1920 000086DD 08                  <1>
  1921 000086DE A0[465F0100]        <1> 	mov	al, [Current_Drv]
  1922 000086E3 A2[A2660100]        <1> 	mov	[RUN_CDRV], al
  1923                              <1> get_dfname_fchar:
  1924 000086E8 AC                  <1> 	lodsb
  1925 000086E9 3C20                <1> 	cmp	al, 20h
  1926 000086EB 74FB                <1> 	je	short get_dfname_fchar
  1927 000086ED 0F82A4000000        <1>         jb      loc_print_dir_call_all
  1928 000086F3 3C2D                <1> 	cmp	al, '-'
  1929 000086F5 7542                <1> 	jne	short loc_print_dir_call_flt
  1930                              <1> get_next_attr_char:
  1931 000086F7 AC                  <1> 	lodsb
  1932 000086F8 3C20                <1> 	cmp	al, 20h
  1933 000086FA 74FB                <1> 	je	short get_next_attr_char
  1934 000086FC 0F820DFFFFFF        <1>         jb      loc_cmd_failed
  1935 00008702 24DF                <1> 	and	al, 0DFh
  1936 00008704 3C44                <1> 	cmp	al, 'D' ; directories only ?
  1937 00008706 7512                <1> 	jne	short pass_only_directories
  1938 00008708 AC                  <1> 	lodsb
  1939 00008709 3C20                <1> 	cmp	al, 20h
  1940 0000870B 0F87FEFEFFFF        <1>         ja      loc_cmd_failed
  1941 00008711 800D[E4670100]10    <1> 	or	byte [AttributesMask], 10h ; ..directory..
  1942 00008718 EB18                <1> 	jmp	short get_dfname_fchar_attr
  1943                              <1> pass_only_directories:
  1944 0000871A 3C46                <1> 	cmp	al, 'F'	; files only ?
  1945 0000871C 0F85B0000000        <1>         jne     check_attr_s
  1946 00008722 AC                  <1> 	lodsb
  1947 00008723 3C20                <1> 	cmp	al, 20h
  1948 00008725 0F87E4FEFFFF        <1>         ja      loc_cmd_failed
  1949 0000872B 800D[E5670100]10    <1> 	or	byte [AttributesMask+1], 10h ; ..except directories..
  1950                              <1> get_dfname_fchar_attr:
  1951 00008732 AC                  <1> 	lodsb
  1952 00008733 3C20                <1> 	cmp	al, 20h
  1953 00008735 74FB                <1> 	je	short get_dfname_fchar_attr
  1954 00008737 725E                <1> 	jb	short loc_print_dir_call_all
  1955                              <1> 
  1956                              <1> loc_print_dir_call_flt:
  1957 00008739 4E                  <1> 	dec	esi
  1958 0000873A BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  1959 0000873F E8AC250000          <1> 	call	parse_path_name
  1960 00008744 7308                <1>  	jnc	short loc_print_dir_change_drv_1
  1961 00008746 3C01                <1> 	cmp	al, 1
  1962 00008748 0F87ECFEFFFF        <1>         ja      loc_run_cmd_failed
  1963                              <1> 
  1964                              <1> loc_print_dir_change_drv_1:
  1965 0000874E 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  1966                              <1> loc_print_dir_change_drv_2:
  1967 00008754 3A15[A2660100]      <1> 	cmp	dl, [RUN_CDRV]
  1968 0000875A 740B                <1> 	je	short loc_print_dir_change_directory 
  1969 0000875C E81BF0FFFF          <1> 	call	change_current_drive
  1970 00008761 0F82D3FEFFFF        <1>         jc      loc_run_cmd_failed
  1971                              <1> loc_print_dir_change_directory:
  1972 00008767 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h ; 0 or 20h ?
  1973 0000876E 761D                <1> 	jna	short pass_print_dir_change_directory
  1974                              <1> 
  1975 00008770 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  1976 00008776 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  1977 0000877B 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  1978 0000877D E8581F0000          <1> 	call	change_current_directory
  1979 00008782 0F82B2FEFFFF        <1>         jc      loc_run_cmd_failed
  1980                              <1> 
  1981                              <1> loc_print_dir_change_prompt_dir_string:
  1982 00008788 E86D1E0000          <1> 	call	change_prompt_dir_string
  1983                              <1> 
  1984                              <1> pass_print_dir_change_directory:
  1985 0000878D BE[28680100]        <1> 	mov	esi, FindFile_Name
  1986 00008792 803E20              <1> 	cmp	byte [esi], 20h ; ; 0 or 20h ?
  1987 00008795 7706                <1> 	ja	short loc_print_dir_call
  1988                              <1> 
  1989                              <1> loc_print_dir_call_all:
  1990 00008797 C7062A2E2A00        <1> 	mov	dword [esi], '*.*'
  1991                              <1> loc_print_dir_call:
  1992 0000879D E87E000000          <1> 	call	print_directory
  1993                              <1> 
  1994 000087A2 8A15[A2660100]      <1> 	mov	dl, [RUN_CDRV]  ; it is set at the beginning
  1995 000087A8 3A15[465F0100]      <1> 	cmp	dl, [Current_Drv]
  1996 000087AE 7406                <1> 	je	short loc_print_dir_call_restore_cdir_retn
  1997 000087B0 E8C7EFFFFF          <1> 	call	change_current_drive 
  1998 000087B5 C3                  <1> 	retn
  1999                              <1> 
  2000                              <1> loc_print_dir_call_restore_cdir_retn:
  2001 000087B6 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  2002 000087BD 7610                <1> 	jna	short pass_print_dir_call_restore_cdir_retn
  2003                              <1> 
  2004 000087BF BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2005 000087C4 31C0                <1> 	xor	eax, eax
  2006 000087C6 88D4                <1> 	mov	ah, dl
  2007 000087C8 01C6                <1> 	add	esi, eax
  2008                              <1> 
  2009 000087CA E864F0FFFF          <1> 	call	restore_current_directory
  2010                              <1> 
  2011                              <1> pass_print_dir_call_restore_cdir_retn:
  2012 000087CF C3                  <1> 	retn
  2013                              <1> 
  2014                              <1> check_attr_s_cap:
  2015 000087D0 24DF                <1> 	and	al, 0DFh
  2016                              <1> check_attr_s:
  2017 000087D2 3C53                <1> 	cmp	al, 'S'
  2018 000087D4 7514                <1> 	jne	short pass_attr_s
  2019 000087D6 800D[E4670100]04    <1> 	or	byte [AttributesMask], 4 ; system
  2020 000087DD AC                  <1> 	lodsb
  2021 000087DE 3C20                <1> 	cmp	al, 20h
  2022 000087E0 0F844CFFFFFF        <1>         je      get_dfname_fchar_attr
  2023 000087E6 72AF                <1> 	jb	short loc_print_dir_call_all
  2024 000087E8 24DF                <1> 	and	al, 0DFh
  2025                              <1> pass_attr_s:
  2026 000087EA 3C48                <1> 	cmp	al, 'H'
  2027 000087EC 7514                <1> 	jne	short pass_attr_h
  2028 000087EE 800D[E4670100]02    <1> 	or	byte [AttributesMask], 2 ; hidden
  2029                              <1> pass_attr_shr:
  2030 000087F5 AC                  <1> 	lodsb
  2031 000087F6 3C20                <1> 	cmp	al, 20h
  2032 000087F8 0F8434FFFFFF        <1>         je      get_dfname_fchar_attr
  2033 000087FE 7297                <1> 	jb	short loc_print_dir_call_all
  2034 00008800 EBCE                <1> 	jmp	short check_attr_s_cap
  2035                              <1> 
  2036                              <1> pass_attr_h:
  2037 00008802 3C52                <1> 	cmp	al, 'R'
  2038 00008804 7509                <1> 	jne	short pass_attr_r
  2039 00008806 800D[E4670100]01    <1> 	or	byte [AttributesMask], 1 ; read only
  2040 0000880D EBE6                <1> 	jmp	short pass_attr_shr
  2041                              <1> 
  2042                              <1> pass_attr_r:
  2043 0000880F 3C41                <1> 	cmp	al, 'A'
  2044 00008811 0F85F8FDFFFF        <1>         jne     loc_cmd_failed
  2045 00008817 800D[E4670100]20    <1> 	or	byte [AttributesMask], 20h ; archive
  2046 0000881E EBD5                <1> 	jmp	short pass_attr_shr
  2047                              <1> 
  2048                              <1> print_directory:
  2049                              <1> 	; 13/05/2016
  2050                              <1> 	; 11/02/2016
  2051                              <1> 	; 10/02/2016
  2052                              <1> 	; 08/02/2016 (TRDOS 386 = TRDOS v2.0)
  2053                              <1> 	; 30/10/2010 ('proc_print_directory')	
  2054                              <1> 	; 19/09/2009
  2055                              <1> 	; 2005 
  2056                              <1> 	; INPUT ->
  2057                              <1> 	;	ESI = Asciiz File/Dir Name Address
  2058                              <1> 
  2059 00008820 56                  <1> 	push	esi
  2060                              <1> 
  2061 00008821 29C0                <1> 	sub	eax, eax
  2062                              <1> 
  2063 00008823 66A3[70680100]      <1> 	mov	word [Dir_Count], ax ; 0
  2064 00008829 66A3[6E680100]      <1> 	mov 	word [File_Count], ax ; 0
  2065 0000882F A3[72680100]        <1> 	mov 	dword [Total_FSize], eax ; 0
  2066                              <1> 
  2067 00008834 E8E2E3FFFF          <1> 	call    clear_screen
  2068                              <1> 	
  2069 00008839 31C9                <1> 	xor	ecx, ecx	
  2070 0000883B 8A2D[465F0100]      <1> 	mov     ch, [Current_Drv] ; DirBuff_Drv - 'A'
  2071 00008841 A0[475F0100]        <1> 	mov     al, [Current_Dir_Drv] 
  2072 00008846 A2[84140100]        <1> 	mov     [Dir_Drive_Name], al
  2073 0000884B BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2074 00008850 01CE                <1> 	add	esi, ecx
  2075                              <1> 
  2076 00008852 E858F9FFFF          <1> 	call	move_volume_name_and_serial_no
  2077 00008857 730C                <1> 	jnc	short print_dir_strlen_check
  2078                              <1> 
  2079 00008859 5E                  <1> 	pop	esi
  2080 0000885A 8A3D[AE5E0100]      <1> 	mov	bh, [ptty] ; [ACTIVE_PAGE]
  2081                              <1> 	;call	beeper
  2082                              <1> 	;retn
  2083 00008860 E95899FFFF          <1> 	jmp	beeper  ; beep ! and return
  2084                              <1> 
  2085                              <1> print_dir_strlen_check:
  2086 00008865 BE[495F0100]        <1> 	mov	esi, Current_Dir_Root
  2087 0000886A BF[21150100]        <1> 	mov	edi, Dir_Str_Root
  2088                              <1> 	
  2089                              <1> 	;xor	ecx, ecx
  2090 0000886F 8A0D[A55F0100]      <1>         mov     cl, [Current_Dir_StrLen]
  2091 00008875 FEC1                <1> 	inc	cl
  2092 00008877 80F940              <1> 	cmp	cl, 64
  2093 0000887A 760D                <1> 	jna	short pass_print_dir_strlen_shorting
  2094 0000887C 46                  <1> 	inc	esi
  2095 0000887D 01CE                <1> 	add	esi, ecx
  2096 0000887F 83EE40              <1> 	sub	esi, 64 
  2097 00008882 47                  <1> 	inc	edi
  2098 00008883 B82E2E2E20          <1> 	mov	eax, '... ' 
  2099 00008888 AB                  <1> 	stosd
  2100                              <1>  
  2101                              <1> pass_print_dir_strlen_shorting:
  2102 00008889 F3A4                <1> 	rep	movsb
  2103                              <1> 
  2104 0000888B BE[77140100]        <1> 	mov	esi, Dir_Drive_Str
  2105 00008890 E870E3FFFF          <1> 	call	print_msg
  2106                              <1> 
  2107 00008895 BE[D6140100]        <1> 	mov	esi, Vol_Serial_Header
  2108 0000889A E866E3FFFF          <1> 	call	print_msg
  2109                              <1> 
  2110 0000889F BE[16150100]        <1> 	mov	esi, Dir_Str_Header
  2111 000088A4 E85CE3FFFF          <1> 	call	print_msg
  2112                              <1> 	
  2113 000088A9 BE[611F0100]        <1> 	mov	esi, next2line
  2114 000088AE E852E3FFFF          <1> 	call	print_msg
  2115                              <1> 
  2116                              <1> loc_print_dir_first_file:
  2117 000088B3 C605[85680100]10    <1> 	mov	byte [PrintDir_RowCounter], 16
  2118 000088BA 66A1[E4670100]      <1> 	mov	ax, [AttributesMask]
  2119 000088C0 5E                  <1> 	pop	esi
  2120                              <1> 
  2121 000088C1 E859020000          <1> 	call	find_first_file
  2122 000088C6 0F826F010000        <1>         jc      loc_dir_ok
  2123                              <1> 	 
  2124                              <1> loc_dfname_use_this:
  2125                              <1> 	; bl =	File Attributes (bh = Long Name Entry Length)
  2126 000088CC F6C310              <1> 	test	bl, 10h  ; Is it a directory?
  2127 000088CF 741B                <1> 	jz	short loc_not_dir
  2128                              <1> 
  2129 000088D1 66FF05[70680100]    <1> 	inc	word [Dir_Count]
  2130 000088D8 89F2                <1> 	mov	edx, esi 	; FindFile_DirEntry address
  2131 000088DA BE[66160100]        <1>  	mov	esi, Type_Dir	; '<DIR>     '
  2132 000088DF BF[7D160100]        <1> 	mov	edi, Dir_Or_FileSize
  2133                              <1> 	; move 10 bytes
  2134 000088E4 A5                  <1> 	movsd
  2135 000088E5 A5                  <1> 	movsd
  2136 000088E6 66A5                <1> 	movsw	    	
  2137 000088E8 89D6                <1> 	mov	esi, edx
  2138 000088EA EB36                <1> 	jmp     short loc_dir_attribute
  2139                              <1> 
  2140                              <1> loc_not_dir:
  2141 000088EC 66FF05[6E680100]    <1> 	inc	word [File_Count]
  2142 000088F3 0105[72680100]      <1> 	add	[Total_FSize], eax
  2143                              <1> 
  2144 000088F9 B90A000000          <1> 	mov	ecx, 10  ; 32 bit divisor
  2145 000088FE 89CF                <1> 	mov	edi, ecx
  2146 00008900 81C7[7D160100]      <1> 	add	edi, Dir_Or_FileSize
  2147                              <1> loc_dir_rdivide:
  2148 00008906 29D2                <1> 	sub	edx, edx
  2149 00008908 F7F1                <1> 	div	ecx 	 ; remainder in dl (< 10)
  2150 0000890A 80C230              <1> 	add     dl, '0'	 ; to make visible (ascii)
  2151 0000890D 4F                  <1> 	dec	edi
  2152 0000890E 8817                <1> 	mov     [edi], dl
  2153 00008910 21C0                <1> 	and	eax, eax
  2154 00008912 75F2                <1> 	jnz	short loc_dir_rdivide
  2155                              <1> 
  2156                              <1> loc_dir_fill_space:
  2157 00008914 81FF[7D160100]      <1> 	cmp     edi, Dir_Or_FileSize
  2158 0000891A 7606                <1> 	jna     short loc_dir_attribute
  2159 0000891C 4F                  <1> 	dec     edi
  2160 0000891D C60720              <1> 	mov     byte [edi], 20h
  2161 00008920 EBF2                <1> 	jmp     short loc_dir_fill_space
  2162                              <1> 
  2163                              <1> loc_dir_attribute:
  2164 00008922 C705[88160100]2020- <1> 	mov	dword [File_Attribute], 20202020h
  2164 0000892A 2020                <1>
  2165                              <1> 
  2166 0000892C 80FB20              <1> 	cmp	bl, 20h  ; Is it an archive file?
  2167 0000892F 7207                <1> 	jb	short loc_dir_pass_arch
  2168 00008931 C605[8B160100]41    <1> 	mov	byte [File_Attribute+3], 'A'
  2169                              <1> 
  2170                              <1> loc_dir_pass_arch:
  2171 00008938 80E307              <1> 	and	bl, 7
  2172 0000893B 7428                <1> 	jz	short loc_dir_file_name
  2173 0000893D 88DF                <1> 	mov	bh, bl
  2174 0000893F 80E303              <1> 	and	bl, 3
  2175 00008942 38DF                <1> 	cmp	bh, bl
  2176 00008944 7607                <1> 	jna	short loc_dir_pass_s
  2177 00008946 C605[88160100]53    <1> 	mov	byte [File_Attribute], 'S'
  2178                              <1> 
  2179                              <1> loc_dir_pass_s:
  2180 0000894D 80E302              <1> 	and     bl,2
  2181 00008950 7407                <1> 	jz      short loc_dir_pass_h
  2182 00008952 C605[89160100]48    <1> 	mov     byte [File_Attribute+1], 'H'
  2183                              <1> loc_dir_pass_h:
  2184 00008959 80E701              <1> 	and     bh,1
  2185 0000895C 7407                <1> 	jz      short loc_dir_file_name
  2186 0000895E C605[8A160100]52    <1> 	mov     byte [File_Attribute+2], 'R'
  2187                              <1> loc_dir_file_name:
  2188                              <1> 	;mov     bx, [esi+18h] ; Date
  2189                              <1> 	;mov     dx, [esi+16h] ; Time
  2190 00008965 8B5E16              <1> 	mov	ebx, [esi+16h]
  2191 00008968 89F1                <1> 	mov	ecx, esi ; FindFile_DirEntry address
  2192 0000896A BF[70160100]        <1> 	mov     edi, File_Name
  2193                              <1> 	; move 8 bytes
  2194 0000896F A5                  <1> 	movsd
  2195 00008970 A5                  <1> 	movsd
  2196 00008971 C60720              <1> 	mov	byte [edi], 20h
  2197 00008974 47                  <1> 	inc	edi
  2198                              <1> 	; move 3 bytes
  2199 00008975 66A5                <1> 	movsw
  2200 00008977 A4                  <1> 	movsb
  2201 00008978 89CE                <1> 	mov	esi, ecx
  2202                              <1> 
  2203                              <1> Dir_Time_start:
  2204                              <1> 	;mov	ax, dx		; Time
  2205 0000897A 6689D8              <1> 	mov	ax, bx
  2206 0000897D 66C1E805            <1> 	shr	ax, 5		; shift right 5 times
  2207 00008981 6683E03F            <1> 	and	ax, 0000111111b	; Minute Mask
  2208 00008985 D40A                <1> 	aam			; Q([AL]/10)->AH
  2209                              <1> 				; R([AL]/10)->AL
  2210                              <1> 				; [AL]+[AH]= Minute as BCD
  2211 00008987 660D3030            <1> 	or	ax, '00'	; Convert to ASCII
  2212 0000898B 86E0                <1> 	xchg	ah, al
  2213 0000898D 66A3[9B160100]      <1> 	mov	[File_Minute], ax
  2214                              <1> 
  2215                              <1> 	;mov	al, dh
  2216 00008993 88F8                <1> 	mov	al, bh
  2217 00008995 C0E803              <1> 	shr	al, 3		; shift right 3 times
  2218 00008998 D40A                <1> 	aam			; [AL]+[AH]= Hours as BCD
  2219 0000899A 660D3030            <1> 	or	ax, '00'
  2220 0000899E 86E0                <1> 	xchg	ah, al
  2221 000089A0 66A3[98160100]      <1> 	mov     [File_Hour], ax
  2222                              <1> 
  2223 000089A6 C1EB10              <1> 	shr	ebx, 16		; BX = Date
  2224                              <1> 	
  2225                              <1> Dir_Date_start:
  2226 000089A9 6689D8              <1> 	mov	ax, bx		; Date
  2227 000089AC 6683E01F            <1> 	and	ax, 00011111b	; Day Mask
  2228 000089B0 D40A                <1> 	aam			; Q([AL]/10)->AH
  2229                              <1> 				; R([AL]/10)->AL
  2230                              <1> 				; [AL]+[AH]= Day as BCD
  2231 000089B2 660D3030            <1> 	or	ax, '00'	; Convert to ASCII
  2232 000089B6 86C4                <1> 	xchg	al, ah
  2233                              <1> 
  2234 000089B8 66A3[8D160100]      <1> 	mov	[File_Day], ax
  2235                              <1> 
  2236 000089BE 6689D8              <1> 	mov	ax, bx
  2237 000089C1 66C1E805            <1> 	shr	ax, 5		; shift right 5 times
  2238 000089C5 6683E00F            <1> 	and	ax, 00001111b	; Month Mask
  2239 000089C9 D40A                <1> 	aam
  2240 000089CB 660D3030            <1> 	or	ax, '00'
  2241 000089CF 86E0                <1> 	xchg	ah, al
  2242 000089D1 66A3[90160100]      <1> 	mov	[File_Month], ax
  2243                              <1> 
  2244 000089D7 6689D8              <1> 	mov	ax, bx
  2245 000089DA 66C1E809            <1> 	shr     ax, 9
  2246 000089DE 6683E07F            <1> 	and	ax, 01111111b	; Result = Year - 1980
  2247 000089E2 6605BC07            <1> 	add	ax, 1980
  2248                              <1> 
  2249 000089E6 B10A                <1> 	mov	cl, 10
  2250 000089E8 F6F1                <1> 	div	cl		; Q -> AL, R -> AH 
  2251 000089EA 80CC30              <1> 	or	ah, '0'
  2252 000089ED 8825[96160100]      <1> 	mov	[File_Year+3], ah
  2253 000089F3 D40A                <1> 	aam
  2254 000089F5 86E0                <1> 	xchg	ah, al
  2255 000089F7 80CC30              <1> 	or	ah, '0'	  ; Convert to ASCII
  2256 000089FA 8825[95160100]      <1> 	mov	[File_Year+2], ah
  2257 00008A00 D40A                <1> 	aam
  2258 00008A02 86C4                <1> 	xchg	al, ah
  2259 00008A04 660D3030            <1> 	or	ax, '00'
  2260 00008A08 66A3[93160100]      <1> 	mov	[File_Year], ax
  2261                              <1> 
  2262                              <1> loc_show_line:
  2263 00008A0E 56                  <1> 	push	esi
  2264 00008A0F BE[70160100]        <1> 	mov     esi, File_Name
  2265 00008A14 E8ECE1FFFF          <1> 	call	print_msg
  2266 00008A19 BE[631F0100]        <1> 	mov	esi, nextline
  2267 00008A1E E8E2E1FFFF          <1> 	call	print_msg
  2268 00008A23 5E                  <1> 	pop	esi
  2269                              <1> 
  2270 00008A24 FE0D[85680100]      <1> 	dec	byte [PrintDir_RowCounter]
  2271 00008A2A 0F84D4000000        <1>         jz      pause_dir_scroll
  2272                              <1> 
  2273                              <1> loc_next_entry:
  2274 00008A30 E899010000          <1> 	call	find_next_file
  2275 00008A35 0F8391FEFFFF        <1>         jnc     loc_dfname_use_this
  2276                              <1> 
  2277                              <1> loc_dir_ok:
  2278 00008A3B B90A000000          <1> 	mov     ecx, 10
  2279 00008A40 66A1[70680100]      <1> 	mov	ax, [Dir_Count]
  2280 00008A46 BF[B1160100]        <1> 	mov	edi, Decimal_Dir_Count
  2281 00008A4B 6639C8              <1> 	cmp	ax, cx ; 10
  2282 00008A4E 7216                <1> 	jb	short pass_ddc
  2283 00008A50 47                  <1> 	inc	edi
  2284 00008A51 6683F864            <1> 	cmp	ax, 100
  2285 00008A55 720F                <1> 	jb	short pass_ddc
  2286 00008A57 47                  <1> 	inc	edi
  2287 00008A58 663DE803            <1> 	cmp	ax, 1000
  2288 00008A5C 7208                <1> 	jb	short pass_ddc
  2289 00008A5E 47                  <1> 	inc	edi
  2290 00008A5F 663D1027            <1> 	cmp	ax, 10000
  2291 00008A63 7201                <1> 	jb	short pass_ddc
  2292 00008A65 47                  <1> 	inc	edi
  2293                              <1> pass_ddc:
  2294 00008A66 886F01              <1> 	mov     [edi+1], ch ; 0
  2295                              <1> loc_ddc_rediv:
  2296 00008A69 31D2                <1> 	xor     edx, edx
  2297 00008A6B 66F7F1              <1> 	div     cx	; 10
  2298 00008A6E 80C230              <1> 	add     dl, '0'
  2299 00008A71 8817                <1> 	mov     [edi], dl
  2300 00008A73 4F                  <1> 	dec     edi
  2301 00008A74 6609C0              <1> 	or	ax, ax
  2302 00008A77 75F0                <1> 	jnz	short loc_ddc_rediv
  2303                              <1> 
  2304 00008A79 66A1[6E680100]      <1> 	mov     ax, [File_Count]
  2305 00008A7F BF[A0160100]        <1> 	mov     edi, Decimal_File_Count
  2306 00008A84 6639C8              <1> 	cmp     ax, cx ; 10
  2307 00008A87 7216                <1> 	jb      short pass_dfc
  2308 00008A89 47                  <1> 	inc     edi
  2309 00008A8A 6683F864            <1> 	cmp     ax, 100
  2310 00008A8E 720F                <1> 	jb      short pass_dfc
  2311 00008A90 47                  <1> 	inc     edi
  2312 00008A91 663DE803            <1> 	cmp     ax, 1000
  2313 00008A95 7208                <1> 	jb      short pass_dfc
  2314 00008A97 47                  <1> 	inc     edi
  2315 00008A98 663D1027            <1> 	cmp     ax, 10000
  2316 00008A9C 7201                <1> 	jb      short pass_dfc
  2317 00008A9E 47                  <1> 	inc     edi
  2318                              <1> pass_dfc:
  2319                              <1> 	;mov    cx, 10
  2320 00008A9F 886F01              <1> 	mov     [edi+1], ch ; 00
  2321                              <1> loc_dfc_rediv:
  2322                              <1> 	;xor	dx, dx
  2323 00008AA2 30D2                <1> 	xor	dl, dl
  2324 00008AA4 66F7F1              <1> 	div	cx
  2325 00008AA7 80C230              <1> 	add	dl, '0'
  2326 00008AAA 8817                <1> 	mov	[edi], dl
  2327 00008AAC 4F                  <1> 	dec	edi
  2328 00008AAD 6609C0              <1> 	or	ax, ax
  2329 00008AB0 75F0                <1> 	jnz	short loc_dfc_rediv
  2330                              <1> 
  2331 00008AB2 BF[84680100]        <1> 	mov     edi, TFS_Dec_End
  2332                              <1>         ;mov    byte [edi], 0
  2333 00008AB7 A1[72680100]        <1> 	mov     eax, [Total_FSize]
  2334                              <1> 	;mov    ecx, 10
  2335                              <1> rediv_tfs_hex:
  2336                              <1> 	;sub	edx, edx
  2337 00008ABC 28D2                <1> 	sub	dl, dl
  2338 00008ABE F7F1                <1> 	div	ecx
  2339 00008AC0 80C230              <1> 	add	dl, '0'
  2340 00008AC3 4F                  <1> 	dec     edi
  2341 00008AC4 8817                <1> 	mov     [edi], dl
  2342 00008AC6 21C0                <1> 	and	eax, eax
  2343 00008AC8 75F2                <1> 	jnz	short rediv_tfs_hex
  2344                              <1> 	
  2345 00008ACA 893D[76680100]      <1> 	mov	[TFS_Dec_Begin], edi
  2346 00008AD0 BE[9E160100]        <1> 	mov	esi, Decimal_File_Count_Header
  2347 00008AD5 E82BE1FFFF          <1> 	call	print_msg
  2348 00008ADA BE[A6160100]        <1> 	mov	esi, str_files
  2349 00008ADF E821E1FFFF          <1> 	call	print_msg
  2350 00008AE4 BE[B7160100]        <1> 	mov	esi, str_dirs
  2351 00008AE9 E817E1FFFF          <1> 	call	print_msg
  2352 00008AEE 8B35[76680100]      <1> 	mov	esi, [TFS_Dec_Begin]
  2353 00008AF4 E80CE1FFFF          <1> 	call	print_msg
  2354 00008AF9 BE[C8160100]        <1> 	mov	esi, str_bytes
  2355 00008AFE E802E1FFFF          <1> 	call	print_msg
  2356                              <1> 
  2357 00008B03 C3                  <1> 	retn
  2358                              <1> 
  2359                              <1> pause_dir_scroll:
  2360 00008B04 28E4                <1> 	sub	ah, ah           
  2361 00008B06 E84F83FFFF          <1> 	call	int16h
  2362 00008B0B 3C1B                <1> 	cmp	al, 1Bh
  2363 00008B0D 0F8428FFFFFF        <1>         je      loc_dir_ok
  2364 00008B13 C605[85680100]10    <1> 	mov	byte [PrintDir_RowCounter], 16 ; Reset counter
  2365 00008B1A E911FFFFFF          <1>         jmp     loc_next_entry
  2366                              <1> 
  2367                              <1> find_first_file:
  2368                              <1> 	; 11/02/2016
  2369                              <1> 	; 10/02/2016
  2370                              <1> 	; 08/02/2016 (TRDOS 386 = TRDOS v2.0)
  2371                              <1> 	; 09/10/2011
  2372                              <1> 	; 17/09/2009
  2373                              <1> 	; 2005
  2374                              <1> 	; INPUT ->
  2375                              <1> 	;	ESI = ASCIIZ File/Dir Name Address (in Current Directory)
  2376                              <1> 	;	AL = Attributes AND mask (The AND result must be equal to AL)
  2377                              <1> 	;	      bit 0 = Read Only
  2378                              <1> 	;	      bir 1 = Hidden
  2379                              <1> 	;	      bit 2 = System
  2380                              <1> 	;	      bit 3 = Volume Label
  2381                              <1> 	;	      bit 4 = Directory
  2382                              <1> 	;	      bit 5 = Archive
  2383                              <1> 	;	      bit 6 = Reserved, must be 0
  2384                              <1> 	;	      bit 7 = Reserved, must be 0
  2385                              <1> 	;       AH = Attributes Negative AND mask (The AND result must be ZERO)
  2386                              <1> 	;
  2387                              <1> 	; OUTPUT ->
  2388                              <1> 	;	CF = 1 -> Error, Error Code in EAX (AL)
  2389                              <1> 	;	CF = 0 ->
  2390                              <1> 	;	     ESI = Directory Entry (FindFile_DirEntry) Location
  2391                              <1> 	;	     EDI = Directory Buffer Directory Entry Location
  2392                              <1> 	;	     EAX = File Size
  2393                              <1> 	;	      BL = Attributes of The File/Directory
  2394                              <1> 	;	      BH = Long Name Yes/No Status (>0 is YES)
  2395                              <1> 	;             DX > 0 : Ambiguous filename chars are used
  2396                              <1> 	;
  2397                              <1> 	; (EAX, EBX, ECX, EDX, ESI, EDI will be changed)
  2398                              <1> 
  2399 00008B1F 66A3[36680100]      <1> 	mov	[FindFile_AttributesMask], ax
  2400 00008B25 BF[38680100]        <1> 	mov	edi, FindFile_DirEntry ; TR-DOS Fullfilename formatted buffer
  2401 00008B2A 31C0                <1> 	xor	eax, eax
  2402 00008B2C B90B000000          <1> 	mov	ecx, 11
  2403 00008B31 F3AB                <1> 	rep	stosd	; 44 bytes
  2404                              <1> 	;stosw		; +2 bytes 
  2405                              <1> 	    
  2406 00008B33 BF[28680100]        <1> 	mov	edi, FindFile_Name ; FFF structure, offset 66
  2407 00008B38 39FE                <1> 	cmp	esi, edi
  2408 00008B3A 7408                <1> 	je	short loc_fff_mfn_ok
  2409 00008B3C 89FA                <1> 	mov	edx, edi 
  2410                              <1> 	 ; move 13 bytes
  2411 00008B3E A5                  <1> 	movsd
  2412 00008B3F A5                  <1> 	movsd
  2413 00008B40 A5                  <1> 	movsd
  2414 00008B41 AA                  <1> 	stosb
  2415 00008B42 89D6                <1> 	mov	esi, edx
  2416                              <1> loc_fff_mfn_ok:
  2417 00008B44 BF[D7670100]        <1> 	mov	edi, Dir_Entry_Name ; Dir Entry Format File Name
  2418 00008B49 E8D7200000          <1> 	call	convert_file_name
  2419 00008B4E 89FE                <1> 	mov	esi, edi ; offset Dir_Entry_Name
  2420                              <1> 
  2421 00008B50 66A1[36680100]      <1> 	mov	ax, [FindFile_AttributesMask]
  2422                              <1> 	;xor	ecx, ecx
  2423 00008B56 30C9                <1> 	xor	cl, cl  
  2424 00008B58 E8D11D0000          <1> 	call	locate_current_dir_file
  2425 00008B5D 726E                <1> 	jc	short loc_fff_retn
  2426                              <1> 	; EDI = Directory Entry
  2427                              <1> 	; EBX = Directory Buffer Entry Index/Number
  2428                              <1> 
  2429                              <1> loc_fff_fnf_ln_check:
  2430 00008B5F 30ED                <1> 	xor	ch, ch 
  2431 00008B61 80F60F              <1> 	xor	dh, 0Fh
  2432 00008B64 7408                <1> 	jz	short loc_fff_longname_yes
  2433 00008B66 882D[35680100]      <1> 	mov	[FindFile_LongNameYes], ch ; 0
  2434 00008B6C EB0C                <1> 	jmp	short loc_fff_longname_no
  2435                              <1> 
  2436                              <1> loc_fff_longname_yes:
  2437                              <1> 	;inc	byte [FindFile_LongNameYes]
  2438 00008B6E 8A0D[42670100]      <1> 	mov	cl, [LFN_EntryLength]  
  2439 00008B74 880D[35680100]      <1> 	mov	[FindFile_LongNameEntryLength], cl ; FindFile_LongNameYes
  2440                              <1> 
  2441                              <1> loc_fff_longname_no:
  2442                              <1> 	;mov	bx, [DirBuff_CurrentEntry]
  2443 00008B7A 66891D[60680100]    <1> 	mov	[FindFile_DirEntryNumber], bx
  2444 00008B81 6689C2              <1> 	mov	dx, ax ; Ambiguous Filename chars used sign > 0
  2445                              <1> 
  2446 00008B84 A0[465F0100]        <1> 	mov	al, [Current_Drv]
  2447 00008B89 A2[E6670100]        <1> 	mov	[FindFile_Drv], al 
  2448                              <1> 
  2449 00008B8E A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
  2450 00008B93 A3[58680100]        <1> 	mov	[FindFile_DirFirstCluster], eax
  2451                              <1> 
  2452 00008B98 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
  2453 00008B9D A3[5C680100]        <1> 	mov	[FindFile_DirCluster], eax
  2454                              <1> 
  2455 00008BA2 66FF05[62680100]    <1> 	inc	word [FindFile_MatchCounter]
  2456                              <1> 
  2457 00008BA9 89FB                <1> 	mov	ebx, edi
  2458 00008BAB 89FE                <1> 	mov	esi, edi
  2459 00008BAD BF[38680100]        <1> 	mov	edi, FindFile_DirEntry
  2460 00008BB2 89F8                <1> 	mov	eax, edi
  2461 00008BB4 B108                <1> 	mov	cl, 8
  2462 00008BB6 F3A5                <1> 	rep	movsd
  2463 00008BB8 89C6                <1> 	mov	esi, eax
  2464 00008BBA 89DF                <1> 	mov	edi, ebx
  2465                              <1> 
  2466 00008BBC A1[54680100]        <1> 	mov	eax, [FindFile_DirEntry+28] ; File Size
  2467                              <1> 
  2468 00008BC1 8A1D[43680100]      <1> 	mov	bl, [FindFile_DirEntry+11] ; File Attributes 
  2469 00008BC7 8A3D[35680100]      <1> 	mov	bh, [FindFile_LongNameYes]
  2470                              <1> 
  2471                              <1> 	;mov	cx, [DirBuff_EntryCounter]
  2472                              <1> 	;mov	[FindFile_DirEntryNumber], cx
  2473                              <1> 	;mov	cx, [FindFile_DirEntryNumber]
  2474                              <1> 	; ecx = 0
  2475                              <1> 
  2476                              <1> loc_fff_retn:
  2477 00008BCD C3                  <1> 	retn
  2478                              <1> 
  2479                              <1> find_next_file:
  2480                              <1> 	; 15/10/2016
  2481                              <1> 	; 10/02/2016
  2482                              <1> 	; 08/02/2016 (TRDOS 386 = TRDOS v2.0)
  2483                              <1> 	; 06/02/2011
  2484                              <1> 	; 17/09/2009
  2485                              <1> 	; 2005
  2486                              <1> 	; INPUT ->
  2487                              <1> 	;	NONE, Find First File Parameters
  2488                              <1> 	; OUTPUT ->
  2489                              <1> 	;	CF = 1 -> Error, Error Code in EAX (AL)
  2490                              <1> 	;	CF = 0 -> 
  2491                              <1> 	;	    ESI = Directory Entry (FindFile_DirEntry) Location
  2492                              <1> 	;	    EDI = Directory Buffer Directory Entry Location
  2493                              <1> 	;	    EAX = File Size
  2494                              <1> 	;	      BL = Attributes of The File/Directory
  2495                              <1> 	;	      BH = Long Name Yes/No Status (>0 is YES)
  2496                              <1> 	;             DX > 0 : Ambiguous filename chars are used 
  2497                              <1> 	;
  2498                              <1> 	; (EAX, EBX, ECX, EDX, ESI, EDI will be changed)
  2499                              <1> 
  2500 00008BCE 66833D[62680100]00  <1> 	cmp	word [FindFile_MatchCounter], 0
  2501 00008BD6 7707                <1> 	ja	short loc_start_search_next_file
  2502                              <1> 
  2503                              <1> loc_fnf_stc_retn:
  2504 00008BD8 F9                  <1> 	stc
  2505                              <1> loc_fnf_ax12h_retn:
  2506 00008BD9 B80C000000          <1> 	mov	eax, 12 ; No More files
  2507                              <1> ;loc_fnf_retn:
  2508 00008BDE C3                  <1> 	retn
  2509                              <1> 
  2510                              <1> loc_start_search_next_file:
  2511 00008BDF 668B1D[60680100]    <1> 	mov	bx, [FindFile_DirEntryNumber]
  2512 00008BE6 6643                <1> 	inc	bx
  2513 00008BE8 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
  2514 00008BEF 7719                <1> 	ja	short loc_cont_search_next_file
  2515                              <1> 
  2516                              <1> loc_fnf_search:
  2517 00008BF1 BE[D7670100]        <1> 	mov	esi, Dir_Entry_Name
  2518 00008BF6 66A1[36680100]      <1> 	mov	ax, [FindFile_AttributesMask]
  2519 00008BFC 6631C9              <1> 	xor	cx, cx
  2520 00008BFF E82E1E0000          <1> 	call	find_directory_entry
  2521 00008C04 0F8355FFFFFF        <1>         jnc     loc_fff_fnf_ln_check
  2522                              <1> 
  2523                              <1> loc_cont_search_next_file:
  2524 00008C0A 31DB                <1> 	xor	ebx, ebx
  2525 00008C0C 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  2526 00008C12 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2527 00008C17 01DE                <1> 	add	esi, ebx
  2528                              <1> 
  2529 00008C19 803D[445F0100]00    <1> 	cmp	byte [Current_Dir_Level], 0
  2530 00008C20 7608                <1> 	jna	short loc_fnf_check_FAT_type
  2531 00008C22 807E0301            <1> 	cmp	byte [esi+LD_FATType], 1
  2532 00008C26 72B1                <1> 	jb	short loc_fnf_ax12h_retn
  2533 00008C28 EB06                <1> 	jmp	short loc_fnf_check_next_cluster
  2534                              <1>  
  2535                              <1> loc_fnf_check_FAT_type:
  2536 00008C2A 807E0303            <1> 	cmp	byte [esi+LD_FATType], 3
  2537 00008C2E 72A9                <1> 	jb	short loc_fnf_ax12h_retn
  2538                              <1> 
  2539                              <1> loc_fnf_check_next_cluster:
  2540 00008C30 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
  2541 00008C35 E8CA370000          <1> 	call	get_next_cluster
  2542 00008C3A 7306                <1> 	jnc	short loc_fnf_load_next_dir_cluster
  2543 00008C3C 09C0                <1> 	or	eax, eax
  2544 00008C3E 7498                <1> 	jz	short loc_fnf_stc_retn
  2545                              <1> 	;mov	eax, 17 ;Drive not ready or read error
  2546 00008C40 F5                  <1>  	cmc	;stc
  2547                              <1> loc_fnf_retn:
  2548 00008C41 C3                  <1> 	retn
  2549                              <1> 
  2550                              <1> loc_fnf_load_next_dir_cluster:
  2551 00008C42 E8A3390000          <1> 	call	load_FAT_sub_directory
  2552 00008C47 72F8                <1> 	jc	short loc_fnf_retn
  2553 00008C49 6631DB              <1> 	xor	bx, bx
  2554 00008C4C 66891D[60680100]    <1> 	mov	[FindFile_DirEntryNumber], bx
  2555 00008C53 EB9C                <1> 	jmp	short loc_fnf_search
  2556                              <1> 
  2557                              <1> get_and_print_longname:
  2558                              <1> 	; 16/10/2016
  2559                              <1> 	; 13/02/2016 (TRDOS 386 = TRDOS v2.0)
  2560                              <1> 	; 24/01/2010
  2561                              <1> 	; 17/10/2009 (CMD_INTR.ASM, 'cmp_cmd_longname')
  2562                              <1> get_longname_fchar:
  2563 00008C55 803E20              <1> 	cmp	byte [esi], 20h
  2564 00008C58 7701                <1> 	ja	short loc_find_longname
  2565                              <1> 	;jb	short loc_longname_retn
  2566                              <1> 	;inc	esi
  2567                              <1> 	;je	short get_longname_fchar
  2568                              <1> ;loc_longname_retn:
  2569 00008C5A C3                  <1> 	retn
  2570                              <1> loc_find_longname:
  2571 00008C5B E839210000          <1> 	call	find_longname
  2572 00008C60 7328                <1> 	jnc	short loc_print_longname
  2573                              <1> 	
  2574 00008C62 08C0                <1> 	or	al, al
  2575 00008C64 741A                <1> 	jz	short loc_longname_not_found
  2576                              <1> 	  
  2577                              <1> 	; 16/10/2016 (15h -> 15, 17)
  2578 00008C66 3C0F                <1> 	cmp	al, 15
  2579 00008C68 0F84B6F7FFFF        <1> 	je	cd_drive_not_ready ; drive not ready
  2580                              <1> 				   ; or
  2581 00008C6E 3C11                <1> 	cmp	al, 17		   ; read error	
  2582 00008C70 0F84AEF7FFFF        <1> 	je	cd_drive_not_ready 
  2583                              <1> 
  2584                              <1> loc_ln_file_dir_not_found:
  2585 00008C76 BE[F2150100]        <1> 	mov	esi, Msg_File_Directory_Not_Found
  2586                              <1> 	;call	print_msg	
  2587                              <1>         ;retn
  2588 00008C7B E985DFFFFF          <1> 	jmp	print_msg
  2589                              <1> 
  2590                              <1> loc_longname_not_found:
  2591 00008C80 BE[11160100]        <1>         mov     esi, Msg_LongName_Not_Found
  2592                              <1> 	;call	print_msg	
  2593                              <1>         ;retn
  2594 00008C85 E97BDFFFFF          <1> 	jmp	print_msg
  2595                              <1> 
  2596                              <1> loc_print_longname:
  2597                              <1> 	;mov	esi, LongFileName
  2598 00008C8A BF[46600100]        <1> 	mov	edi, TextBuffer
  2599 00008C8F 57                  <1> 	push	edi 
  2600 00008C90 3C00                <1> 	cmp	al, 0
  2601 00008C92 7708                <1> 	ja	short loc_print_longname_1
  2602                              <1> loc_print_FS_longname: ; Singlix FS (64 byte ASCIIZ file name)
  2603 00008C94 AC                  <1> 	lodsb
  2604 00008C95 AA                  <1> 	stosb  
  2605 00008C96 08C0                <1> 	or	al, al
  2606 00008C98 75FA                <1> 	jnz	short loc_print_FS_longname
  2607 00008C9A EB07                <1> 	jmp	short loc_print_longname_2
  2608                              <1> 	;
  2609                              <1> loc_print_longname_1: ; MS Windows long name (UNICODE chars)
  2610 00008C9C 66AD                <1> 	lodsw
  2611 00008C9E AA                  <1> 	stosb  
  2612 00008C9F 08C0                <1> 	or	al, al
  2613 00008CA1 75F9                <1> 	jnz	short loc_print_longname_1
  2614                              <1> 	;
  2615                              <1> loc_print_longname_2:	
  2616 00008CA3 5E                  <1> 	pop	esi
  2617 00008CA4 E85CDFFFFF          <1> 	call	print_msg
  2618 00008CA9 BE[631F0100]        <1>   	mov	esi, nextline
  2619                              <1> 	;call	print_msg
  2620                              <1> 	;retn
  2621 00008CAE E952DFFFFF          <1> 	jmp	print_msg	
  2622                              <1> 
  2623                              <1> show_file:
  2624                              <1> 	; 18/02/2016
  2625                              <1> 	; 17/02/2016
  2626                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  2627                              <1> 	; 13/09/2011 (CMD_INTR.ASM, 'cmp_cmd_show')
  2628                              <1> 	; 08/11/2009
  2629                              <1> 
  2630                              <1> loc_show_parse_path_name:
  2631 00008CB3 BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  2632 00008CB8 E833200000          <1> 	call	parse_path_name
  2633 00008CBD 0F824CF9FFFF        <1> 	jc	loc_cmd_failed
  2634                              <1> 
  2635                              <1> loc_show_check_filename_exists:
  2636 00008CC3 BE[28680100]        <1> 	mov	esi, FindFile_Name
  2637 00008CC8 803E20              <1> 	cmp	byte [esi], 20h
  2638 00008CCB 0F863EF9FFFF        <1> 	jna	loc_cmd_failed
  2639                              <1> 
  2640                              <1> 	; 15/02/2016 (invalid file name check)
  2641 00008CD1 E807020000          <1> 	call	check_filename 	
  2642 00008CD6 730A                <1> 	jnc	short loc_show_change_drv
  2643                              <1> 
  2644 00008CD8 BE[DE160100]        <1> 	mov	esi, Msg_invalid_name_chars
  2645 00008CDD E923DFFFFF          <1> 	jmp	print_msg
  2646                              <1>    
  2647                              <1> loc_show_change_drv:
  2648 00008CE2 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  2649 00008CE8 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  2650 00008CEE 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  2651 00008CF4 38F2                <1> 	cmp	dl, dh
  2652 00008CF6 740B                <1> 	je	short loc_show_change_directory
  2653 00008CF8 E87FEAFFFF          <1> 	call	change_current_drive
  2654                              <1> 	;jc	loc_file_rw_cmd_failed
  2655 00008CFD 0F8237F9FFFF        <1> 	jc	loc_run_cmd_failed
  2656                              <1> 
  2657                              <1> loc_show_change_directory:
  2658 00008D03 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  2659 00008D0A 7618                <1> 	jna	short loc_findload_showfile
  2660                              <1> 
  2661 00008D0C FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  2662 00008D12 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  2663 00008D17 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  2664 00008D19 E8BC190000          <1> 	call	change_current_directory
  2665                              <1> 	;jc	loc_file_rw_cmd_failed
  2666 00008D1E 0F8216F9FFFF        <1> 	jc	loc_run_cmd_failed
  2667                              <1> 
  2668                              <1> ;loc_show_change_prompt_dir_string:
  2669                              <1> 	;call	change_prompt_dir_string
  2670                              <1> 
  2671                              <1> loc_findload_showfile:
  2672                              <1> 	; 15/02/2016
  2673 00008D24 BE[28680100]        <1> 	mov	esi, FindFile_Name
  2674 00008D29 BF[D7670100]        <1> 	mov	edi, Dir_Entry_Name ; Dir Entry Format File Name
  2675 00008D2E E8F21E0000          <1> 	call	convert_file_name
  2676 00008D33 89FE                <1> 	mov	esi, edi ; offset Dir_Entry_Name
  2677                              <1> 
  2678 00008D35 28C0                <1> 	sub	al, al	; Attrib AND mask = 0
  2679                              <1> 	; Directory attribute : 10h
  2680                              <1> 	; Volume name attribute: 8h
  2681 00008D37 B418                <1> 	mov	ah, 00011000b ; 18h (Attrib NAND, AND --> zero mask)
  2682                              <1> 	;
  2683 00008D39 6631C9              <1> 	xor	cx, cx  
  2684 00008D3C E8ED1B0000          <1> 	call	locate_current_dir_file
  2685                              <1> 	;jc	loc_file_rw_cmd_failed
  2686 00008D41 0F82F3F8FFFF        <1> 	jc	loc_run_cmd_failed
  2687                              <1> 
  2688                              <1> loc_show_load_file:
  2689                              <1> 	; EDI = Directory Entry
  2690 00008D47 668B4714            <1> 	mov	ax, [edi+DirEntry_FstClusHI] ; First Cluster High Word
  2691 00008D4B C1E010              <1> 	shl	eax, 16
  2692 00008D4E 668B471A            <1> 	mov	ax, [edi+DirEntry_FstClusLO] ; First Cluster Low Word
  2693 00008D52 A3[90680100]        <1> 	mov	[Show_Cluster], eax
  2694 00008D57 8B471C              <1> 	mov	eax, [edi+DirEntry_FileSize] ; File Size
  2695 00008D5A 21C0                <1> 	and	eax, eax ; Empty file !
  2696 00008D5C 0F8491000000        <1>         jz      end_of_show_file 
  2697 00008D62 A3[94680100]        <1> 	mov	[Show_FileSize], eax
  2698 00008D67 31C0                <1> 	xor	eax, eax
  2699 00008D69 A3[98680100]        <1> 	mov	[Show_FilePointer], eax ; 0
  2700 00008D6E 66A3[9C680100]      <1> 	mov	[Show_ClusterPointer], ax ; 0
  2701 00008D74 29DB                <1> 	sub	ebx, ebx
  2702 00008D76 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  2703 00008D7C BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2704 00008D81 01DE                <1> 	add	esi, ebx
  2705 00008D83 8935[8C680100]      <1> 	mov	[Show_LDDDT], esi ; Logical DOS Drv Description Table addr
  2706                              <1> 
  2707 00008D89 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0	
  2708 00008D8D 7713                <1> 	ja	short loc_show_calculate_cluster_size
  2709                              <1> 	; Singlix FS
  2710                              <1> 	; First Cluster Number is FDT number (in compatibility buffer)
  2711 00008D8F 8B15[90680100]      <1> 	mov	edx, [Show_Cluster] ; Compatibility dir. buffer value (FDT)	
  2712 00008D95 8915[88680100]      <1> 	mov	[Show_FDT], edx
  2713 00008D9B 31C0                <1> 	xor	eax, eax
  2714 00008D9D A3[90680100]        <1> 	mov	[Show_Cluster], eax ; Sector index  = 0
  2715                              <1> 				    ; (next time it will be 1)			
  2716                              <1> loc_show_calculate_cluster_size:
  2717 00008DA2 668B5E11            <1> 	mov	bx, [esi+LD_BPB+BPB_BytsPerSec] ; FAT 12-16-32 (512)
  2718                              <1> 	; BX = 512 = [esi+LD_FS_BytesPerSec] ; Singlix FS	
  2719 00008DA6 8A4613              <1> 	mov	al, [esi+LD_BPB+BPB_SecPerClust] ; FAT 12-16-32 (<= 128)
  2720                              <1> 	; AL = 1 = [esi+LD_FS_Reserved2] ; SectPerClust for Singlix FS
  2721 00008DA9 F7E3                <1> 	mul	ebx	
  2722                              <1> 
  2723                              <1> 	;cmp	eax, 65536 ; non-compatible (very big) cluster size
  2724                              <1> 	;ja	short end_of_show_file	
  2725 00008DAB 66A3[9E680100]      <1> 	mov	[Show_ClusterSize], ax
  2726                              <1> 
  2727                              <1> loc_start_show_file:
  2728 00008DB1 BE[631F0100]        <1> 	mov	esi, nextline
  2729 00008DB6 E84ADEFFFF          <1> 	call	print_msg
  2730                              <1> 
  2731 00008DBB A1[90680100]        <1> 	mov	eax, [Show_Cluster]
  2732 00008DC0 C605[A0680100]17    <1> 	mov	byte [Show_RowCount], 23
  2733                              <1> 
  2734                              <1> 	; 17/02/2016
  2735 00008DC7 8B35[8C680100]      <1> 	mov	esi, [Show_LDDDT]
  2736                              <1> 
  2737                              <1> loc_show_next_cluster:
  2738                              <1> 	; 15/02/2016
  2739 00008DCD BB00000700          <1> 	mov	ebx, Cluster_Buffer ; 70000h (for current TRDOS 386 version)
  2740                              <1> 	; ESI = Logical DOS drv description table address
  2741 00008DD2 E851380000          <1> 	call	read_cluster
  2742                              <1> 	;jc	loc_file_rw_cmd_failed
  2743 00008DD7 0F825DF8FFFF        <1> 	jc	loc_run_cmd_failed
  2744                              <1> 
  2745 00008DDD 31DB                <1> 	xor 	ebx, ebx
  2746                              <1> loc_show_next_byte:
  2747 00008DDF 803D[A0680100]00    <1> 	cmp	byte [Show_RowCount], 0
  2748 00008DE6 7521                <1> 	jne	short pass_show_wait_for_key
  2749 00008DE8 30E4                <1> 	xor	ah, ah
  2750 00008DEA E86B80FFFF          <1> 	call	int16h
  2751 00008DEF 3C1B                <1> 	cmp	al, 1Bh
  2752 00008DF1 750F                <1> 	jne	short pass_exit_show
  2753                              <1> end_of_show_file:
  2754                              <1> pass_show_file:
  2755 00008DF3 BE[631F0100]        <1> 	mov	esi, nextline
  2756 00008DF8 E808DEFFFF          <1> 	call	print_msg
  2757 00008DFD E94B010000          <1> 	jmp	loc_file_rw_restore_retn
  2758                              <1> 
  2759                              <1> pass_exit_show:
  2760 00008E02 C605[A0680100]14    <1> 	mov	byte [Show_RowCount], 20
  2761                              <1> pass_show_wait_for_key:
  2762 00008E09 81C300000700        <1> 	add	ebx, Cluster_Buffer
  2763 00008E0F 8A03                <1> 	mov	al, [ebx]
  2764 00008E11 3C0D                <1> 	cmp	al, 0Dh
  2765 00008E13 0F8590000000        <1>         jne     loc_show_check_tab_space
  2766 00008E19 FE0D[A0680100]      <1> 	dec	byte [Show_RowCount]
  2767                              <1> pass_show_dec_rowcount:
  2768 00008E1F B307                <1> 	mov	bl, 7 ; (light gray character color, black background)
  2769 00008E21 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE] ; [ptty]
  2770 00008E27 E8A992FFFF          <1> 	call	_write_tty
  2771                              <1> loc_show_check_eof:
  2772 00008E2C FF05[98680100]      <1> 	inc	dword [Show_FilePointer]
  2773 00008E32 A1[98680100]        <1> 	mov	eax, [Show_FilePointer]
  2774 00008E37 3B05[94680100]      <1> 	cmp	eax, [Show_FileSize]
  2775 00008E3D 73B4                <1> 	jnb	short end_of_show_file
  2776 00008E3F 66FF05[9C680100]    <1> 	inc	word [Show_ClusterPointer]
  2777 00008E46 0FB71D[9C680100]    <1> 	movzx	ebx, word [Show_ClusterPointer]
  2778                              <1> 
  2779                              <1> 	; 17/02/2016
  2780                              <1> 	; (sector boundary -9 bits- check, 512 = 0)
  2781 00008E4D 66F7C3FF01          <1>         test    bx, 1FFh ;  1 to 511
  2782 00008E52 758B                <1> 	jnz	short loc_show_next_byte
  2783                              <1> 
  2784                              <1> 	; 16/02/2016
  2785 00008E54 8B35[8C680100]      <1> 	mov	esi, [Show_LDDDT]
  2786                              <1> 	;
  2787 00008E5A 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  2788 00008E5E 7719                <1> 	ja	short loc_show_check_fat_cluster_size
  2789                              <1> 
  2790                              <1> 	; Singlix FS
  2791                              <1> 	; 1 sector, more... (cluster size = 1 sector)
  2792 00008E60 A1[90680100]        <1> 	mov	eax, [Show_Cluster]
  2793 00008E65 40                  <1> 	inc	eax
  2794 00008E66 A3[90680100]        <1> 	mov	[Show_Cluster], eax
  2795                              <1> 
  2796 00008E6B 6621DB              <1> 	and	bx, bx ; 65536 -> 0
  2797 00008E6E 0F856BFFFFFF        <1>         jnz	loc_show_next_byte
  2798 00008E74 E954FFFFFF          <1> 	jmp     loc_show_next_cluster
  2799                              <1> 	 
  2800                              <1> loc_show_check_fat_cluster_size:
  2801                              <1> 	; 17/02/2016
  2802 00008E79 663B1D[9E680100]    <1> 	cmp	bx, [Show_ClusterSize] ; cluster size in bytes
  2803 00008E80 0F8259FFFFFF        <1>         jb	loc_show_next_byte
  2804 00008E86 66C705[9C680100]00- <1> 	mov	word [Show_ClusterPointer], 0
  2804 00008E8E 00                  <1>
  2805                              <1> 
  2806 00008E8F A1[90680100]        <1> 	mov	eax, [Show_Cluster]
  2807                              <1> 	;mov	esi, [Show_LDDDT]
  2808                              <1> loc_show_get_next_cluster:
  2809 00008E94 E86B350000          <1> 	call	get_next_cluster
  2810                              <1> 	;jc	loc_file_rw_cmd_failed
  2811 00008E99 0F829BF7FFFF        <1> 	jc	loc_run_cmd_failed
  2812                              <1> loc_show_update_ccluster:
  2813 00008E9F A3[90680100]        <1> 	mov	[Show_Cluster], eax			
  2814 00008EA4 E924FFFFFF          <1>         jmp     loc_show_next_cluster
  2815                              <1> 
  2816                              <1> loc_show_check_tab_space:
  2817 00008EA9 3C09                <1> 	cmp	al, 09h
  2818 00008EAB 0F856EFFFFFF        <1>         jne     pass_show_dec_rowcount
  2819                              <1> loc_show_put_tab_space:
  2820 00008EB1 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE] ; [ptty]
  2821 00008EB7 E88C8EFFFF          <1> 	call	get_cpos
  2822                              <1> 	; dl = cursor column
  2823 00008EBC 80E207              <1> 	and	dl, 7 ; 18/02/2016
  2824                              <1> 	;shr	bh, 1 ; [ACTIVE_PAGE]
  2825 00008EBF 8A3D[AE5E0100]      <1> 	mov	bh, [ACTIVE_PAGE]
  2826 00008EC5 B307                <1> 	mov	bl, 7 ; color attribute
  2827                              <1> loc_show_put_space_chars:
  2828 00008EC7 B020                <1> 	mov	al, 20h ; space
  2829                              <1> 	;mov	bh, [ACTIVE_PAGE] ; [ptty]
  2830                              <1> 	;mov	bl, 7 ; color attribute
  2831                              <1> 	;push	dx
  2832 00008EC9 52                  <1> 	push	edx ; 29/12/2017
  2833 00008ECA E80692FFFF          <1> 	call	_write_tty
  2834 00008ECF 5A                  <1> 	pop	edx ; 29/12/2017
  2835                              <1> 	;pop	dx
  2836                              <1> 	; 18/02/2016
  2837 00008ED0 80FA07              <1> 	cmp	dl, 7
  2838 00008ED3 0F8353FFFFFF        <1> 	jnb	loc_show_check_eof
  2839 00008ED9 FEC2                <1> 	inc	dl
  2840 00008EDB EBEA                <1> 	jmp	short loc_show_put_space_chars
  2841                              <1> 
  2842                              <1> check_filename:
  2843                              <1> 	; 10/10/2016
  2844                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  2845                              <1> 	; 07/08/2010 (FILE.ASM, 'proc_check_filename')
  2846                              <1> 	; 10/07/2010
  2847                              <1> 	; Derived from 'proc_check_filename'
  2848                              <1> 	; in the old TRDOS.ASM (09/02/2005).
  2849                              <1> 	;
  2850                              <1> 	; INPUT -> 
  2851                              <1> 	;	ESI = Dot File Name Location
  2852                              <1> 	; OUTPUT ->
  2853                              <1> 	;	cf = 1 -> error code in AL
  2854                              <1> 	;	     AL = ERR_INV_FILE_NAME (=26)
  2855                              <1> 	;		  Invalid file name chars   
  2856                              <1> 	;	cf = 0 -> valid file name
  2857                              <1> 	; 
  2858                              <1> 	;(EAX, ECX, EDI will be changed)
  2859                              <1> 
  2860                              <1> check_invalid_filename_chars:
  2861                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  2862                              <1> 	; 10/07/2010 (FILE.ASM, 'proc_check_invalid_filename_chars')
  2863                              <1> 	; 10/02/2010
  2864                              <1> 	; Derived from 'proc_check_invalid_filename_chars'
  2865                              <1> 	; in the old TRDOS.ASM (09/02/2005).
  2866                              <1> 	;
  2867                              <1> 	; INPUT -> 
  2868                              <1> 	;	ESI = ASCIIZ FileName
  2869                              <1> 	; OUTPUT ->
  2870                              <1> 	;	cf = 1 -> invalid
  2871                              <1> 	;	cf = 0 -> valid
  2872                              <1> 	; 
  2873                              <1> 	;(EAX, ECX, EDI will be changed)
  2874                              <1>   
  2875 00008EDD 56                  <1> 	push	esi
  2876                              <1> 
  2877 00008EDE BF[C6130100]        <1>         mov     edi, invalid_fname_chars
  2878 00008EE3 AC                  <1> 	lodsb
  2879                              <1> check_filename_next_char:
  2880 00008EE4 B914000000          <1> 	mov	ecx, sizeInvFnChars
  2881 00008EE9 BF[C6130100]        <1> 	mov	edi, invalid_fname_chars
  2882                              <1> loc_scan_invalid_filename_char:
  2883 00008EEE AE                  <1> 	scasb 
  2884 00008EEF 741F                <1> 	je	short loc_invalid_filename_stc 
  2885 00008EF1 E2FB                <1> 	loop	loc_scan_invalid_filename_char
  2886 00008EF3 AC                  <1> 	lodsb
  2887 00008EF4 3C1F                <1> 	cmp	al, 1Fh  ; 20h and above 
  2888 00008EF6 77EC                <1> 	ja	short check_filename_next_char
  2889                              <1> 
  2890                              <1> check_filename_dot:
  2891 00008EF8 8B3424              <1> 	mov	esi, [esp]
  2892                              <1> 
  2893 00008EFB B421                <1> 	mov	ah, 21h
  2894 00008EFD B908000000          <1> 	mov	ecx, 8
  2895                              <1> loc_check_filename_next_char:
  2896 00008F02 AC                  <1> 	lodsb
  2897 00008F03 3C2E                <1> 	cmp	al, 2Eh
  2898 00008F05 7511                <1> 	jne	short pass_check_fn_dot_check
  2899                              <1> loc_check_filename_ext_0:
  2900 00008F07 AC                  <1> 	lodsb
  2901 00008F08 38E0                <1> 	cmp	al, ah ; 21h
  2902 00008F0A 7205                <1> 	jb	short loc_invalid_filename
  2903 00008F0C 3C2E                <1> 	cmp	al, 2Eh
  2904 00008F0E 7519                <1> 	jne	short loc_check_filename_ext_1
  2905                              <1> 
  2906                              <1> loc_invalid_filename_stc:
  2907                              <1> loc_check_fn_stc_rtn:
  2908 00008F10 F9                  <1> 	stc
  2909                              <1> loc_invalid_filename:
  2910                              <1> 	; 10/10/2016 (0Bh -> 26)
  2911 00008F11 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME ; (=26)
  2912                              <1> 	; Invalid file name chars
  2913                              <1> loc_check_fn_rtn:
  2914 00008F16 5E                  <1> 	pop	esi
  2915 00008F17 C3                  <1> 	retn
  2916                              <1> 
  2917                              <1> pass_check_fn_dot_check:
  2918 00008F18 38E0                <1> 	cmp	al, ah ; 21h
  2919 00008F1A 7224                <1> 	jb	short loc_check_fn_clc_rtn
  2920 00008F1C E2E4                <1> 	loop	loc_check_filename_next_char
  2921 00008F1E AC                  <1> 	lodsb
  2922 00008F1F 38E0                <1> 	cmp	al, ah ; 21h
  2923 00008F21 721D                <1> 	jb	short loc_check_fn_clc_rtn
  2924 00008F23 3C2E                <1> 	cmp	al, 2Eh
  2925 00008F25 75E9                <1> 	jne	short loc_check_fn_stc_rtn
  2926 00008F27 EBDE                <1> 	jmp	short loc_check_filename_ext_0
  2927                              <1> 
  2928                              <1> loc_check_filename_ext_1:
  2929 00008F29 AC                  <1> 	lodsb
  2930 00008F2A 38E0                <1> 	cmp	al, ah ; 21h
  2931 00008F2C 7212                <1> 	jb	short loc_check_fn_clc_rtn
  2932 00008F2E 3C2E                <1> 	cmp	al, 2Eh
  2933 00008F30 74DE                <1> 	je	short loc_check_fn_stc_rtn
  2934 00008F32 AC                  <1> 	lodsb
  2935 00008F33 38E0                <1> 	cmp	al, ah ; 21h
  2936 00008F35 7209                <1> 	jb	short loc_check_fn_clc_rtn
  2937 00008F37 3C2E                <1> 	cmp	al, 2Eh
  2938 00008F39 74D5                <1> 	je	short loc_check_fn_stc_rtn
  2939 00008F3B AC                  <1> 	lodsb
  2940 00008F3C 38E0                <1> 	cmp	al, ah ; 21h
  2941 00008F3E 73D0                <1> 	jnb	short loc_check_fn_stc_rtn
  2942                              <1> 
  2943                              <1> loc_check_fn_clc_rtn:
  2944 00008F40 5E                  <1> 	pop	esi
  2945 00008F41 F8                  <1> 	clc
  2946 00008F42 C3                  <1> 	retn
  2947                              <1> 
  2948                              <1> loc_print_deleted_message:
  2949 00008F43 BE[B3170100]        <1> 	mov	esi, Msg_Deleted
  2950 00008F48 E8B8DCFFFF          <1> 	call	print_msg
  2951                              <1> 
  2952                              <1> 	;clc
  2953                              <1> 
  2954                              <1> loc_file_rw_restore_retn:
  2955                              <1> 	; 15/02/2016 (TRDOS 386 = TRDOS v2.0)
  2956                              <1> 	; 28/02/2010 (CMD_INTR.ASM)
  2957                              <1> loc_file_rw_cmd_failed:
  2958 00008F4D 9C                  <1> 	pushf 
  2959 00008F4E E84FF7FFFF          <1> 	call	restore_cdir_after_cmd_fail	
  2960 00008F53 9D                  <1> 	popf
  2961 00008F54 720D                <1> 	jc	short loc_file_rw_check_write_fault
  2962 00008F56 C3                  <1> 	retn
  2963                              <1> 
  2964                              <1> loc_permission_denied:
  2965                              <1> 	; 27/02/2016
  2966 00008F57 BE[C0170100]        <1> 	mov	esi, Msg_Permission_Denied
  2967 00008F5C E8A4DCFFFF          <1> 	call	print_msg
  2968 00008F61 EBEA                <1> 	jmp	short loc_file_rw_restore_retn
  2969                              <1> 
  2970                              <1> loc_file_rw_check_write_fault:
  2971                              <1> 	;cmp	al, 1Dh ; Write Fault
  2972 00008F63 3C12                <1>         cmp	al, 18 ; 05/11/2016
  2973 00008F65 0F85D4F6FFFF        <1> 	jne     loc_run_cmd_failed_cmp_al
  2974 00008F6B BE[A7150100]        <1> 	mov	esi, Msg_Not_Ready_Write_Err
  2975                              <1> 	;call	print_msg
  2976                              <1> 	;retn
  2977 00008F70 E990DCFFFF          <1> 	jmp	print_msg
  2978                              <1> 
  2979                              <1> make_directory:
  2980                              <1> 	; 21/02/2016 (TRDOS 386 = TRDOS v2.0)
  2981                              <1> 	; 12/03/2011 (CMD_INTR.ASM, 'cmp_cmd_mkdir')
  2982                              <1> 	; 14/08/2010
  2983                              <1> 	; 10/07/2010
  2984                              <1> 	; 29/11/2009
  2985                              <1> 	;
  2986                              <1> get_mkdir_fchar:
  2987                              <1> 	; esi = directory name
  2988 00008F75 803E20              <1> 	cmp	byte [esi], 20h
  2989 00008F78 7701                <1>         ja	short loc_mkdir_parse_path_name
  2990                              <1> 
  2991                              <1> loc_mkdir_nodirname_retn:
  2992 00008F7A C3                  <1> 	retn
  2993                              <1> 
  2994                              <1> loc_mkdir_parse_path_name:
  2995 00008F7B BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  2996 00008F80 E86B1D0000          <1>         call    parse_path_name
  2997 00008F85 0F8284F6FFFF        <1> 	jc	loc_cmd_failed
  2998                              <1> 
  2999                              <1> loc_mkdir_check_dirname_exists:
  3000 00008F8B BE[28680100]        <1> 	mov	esi, FindFile_Name
  3001 00008F90 803E20              <1> 	cmp	byte [esi], 20h
  3002 00008F93 0F8676F6FFFF        <1> 	jna	loc_cmd_failed
  3003 00008F99 8935[A4680100]      <1> 	mov	[DelFile_FNPointer], esi
  3004 00008F9F E839FFFFFF          <1> 	call	check_filename
  3005 00008FA4 7259                <1> 	jc	short loc_mkdir_invalid_dir_name_chars
  3006                              <1> 
  3007                              <1> loc_mkdir_drv:
  3008 00008FA6 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  3009 00008FAC 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  3010                              <1> 	
  3011 00008FB2 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  3012 00008FB8 38F2                <1> 	cmp	dl, dh
  3013 00008FBA 7407                <1> 	je	short loc_mkdir_change_directory
  3014                              <1> 
  3015 00008FBC E8BBE7FFFF          <1> 	call	change_current_drive
  3016 00008FC1 728A                <1> 	jc	loc_file_rw_cmd_failed
  3017                              <1> 
  3018                              <1> loc_mkdir_change_directory:
  3019 00008FC3 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  3020 00008FCA 7614                <1> 	jna	short loc_mkdir_find_directory
  3021                              <1> 
  3022 00008FCC FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3023 00008FD2 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  3024 00008FD7 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  3025 00008FD9 E8FC160000          <1> 	call	change_current_directory
  3026 00008FDE 722E                <1> 	jc	short loc_mkdir_check_error_code
  3027                              <1> 
  3028                              <1> ;loc_mkdir_change_prompt_dir_string:
  3029                              <1> 	;call	change_prompt_dir_string
  3030                              <1> 
  3031                              <1> loc_mkdir_find_directory:
  3032                              <1> 	;mov	esi, FindFile_Name
  3033 00008FE0 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3034                              <1> 	;xor	eax, eax
  3035 00008FE6 6631C0              <1> 	xor	ax, ax ; any name (dir, file, volume)
  3036 00008FE9 E831FBFFFF          <1> 	call	find_first_file
  3037 00008FEE 721E                <1> 	jc	short loc_mkdir_check_error_code
  3038                              <1> 
  3039                              <1> loc_mkdir_directory_found:
  3040 00008FF0 BE[0B170100]        <1> 	mov	esi, Msg_Name_Exists
  3041 00008FF5 E80BDCFFFF          <1> 	call	print_msg
  3042                              <1> 
  3043 00008FFA E94EFFFFFF          <1>         jmp     loc_file_rw_restore_retn
  3044                              <1> 
  3045                              <1> loc_mkdir_invalid_dir_name_chars:
  3046 00008FFF BE[DE160100]        <1> 	mov	esi, Msg_invalid_name_chars
  3047 00009004 E8FCDBFFFF          <1> 	call	print_msg
  3048                              <1> 
  3049 00009009 E93FFFFFFF          <1>         jmp     loc_file_rw_restore_retn
  3050                              <1> 
  3051                              <1> loc_mkdir_check_error_code:
  3052 0000900E 3C02                <1> 	cmp	al, 2
  3053                              <1> 	;je	short loc_mkdir_directory_not_found
  3054 00009010 7406                <1> 	je	short loc_mkdir_ask_for_yes_no
  3055 00009012 F9                  <1> 	stc
  3056 00009013 E935FFFFFF          <1>         jmp     loc_file_rw_cmd_failed
  3057                              <1> 
  3058                              <1> loc_mkdir_directory_not_found:
  3059                              <1> loc_mkdir_ask_for_yes_no:
  3060 00009018 BE[2C170100]        <1> 	mov	esi, Msg_DoYouWantMkdir
  3061 0000901D E8E3DBFFFF          <1> 	call	print_msg
  3062 00009022 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3063 00009028 E8D8DBFFFF          <1> 	call	print_msg
  3064 0000902D BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  3065 00009032 E8CEDBFFFF          <1> 	call	print_msg
  3066                              <1> 
  3067 00009037 C605[55170100]20    <1> 	mov	byte [Y_N_nextline], 20h
  3068                              <1> 
  3069                              <1> loc_mkdir_ask_again:
  3070 0000903E 30E4                <1> 	xor	ah, ah
  3071 00009040 E8157EFFFF          <1> 	call	int16h
  3072 00009045 3C1B                <1> 	cmp	al, 1Bh
  3073                              <1> 	;je	short loc_do_not_make_directory
  3074 00009047 7439                <1> 	je	short loc_mkdir_y_n_escape
  3075 00009049 24DF                <1> 	and	al, 0DFh ; y -> Y, n -> N
  3076 0000904B 3C59                <1> 	cmp	al, 'Y' ; 'yes'
  3077 0000904D 7404                <1> 	je	short loc_mkdir_yes_make_directory
  3078 0000904F 3C4E                <1> 	cmp	al, 'N' ; 'no'
  3079 00009051 75EB                <1> 	jne	short loc_mkdir_ask_again
  3080                              <1> 
  3081                              <1> loc_do_not_make_directory:
  3082                              <1> loc_mkdir_yes_make_directory:
  3083 00009053 E82E000000          <1> 	call	y_n_answer ; 29/12/2017
  3084                              <1> 	;cmp	al, 'Y' ; 'yes'
  3085                              <1> 	;cmc
  3086                              <1>         ;jnc	loc_file_rw_restore_retn
  3087 00009058 3C4E                <1> 	cmp	al, 'N' ; 'no'
  3088 0000905A 0F84EDFEFFFF        <1>         je	loc_file_rw_restore_retn  
  3089                              <1> 
  3090                              <1> loc_mkdir_call_make_sub_directory:
  3091 00009060 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3092 00009066 B110                <1> 	mov	cl, 10h ; Directory attributes 
  3093 00009068 E8821D0000          <1> 	call	make_sub_directory
  3094                              <1> loc_rename_file_ok: ; 06/03/2016
  3095 0000906D 0F82DAFEFFFF        <1>         jc	loc_file_rw_cmd_failed
  3096                              <1> move_source_file_to_destination_OK:
  3097 00009073 BE[59170100]        <1> 	mov	esi, Msg_OK
  3098 00009078 E888DBFFFF          <1> 	call	print_msg
  3099 0000907D E9CBFEFFFF          <1> 	jmp	loc_file_rw_restore_retn
  3100                              <1> 
  3101                              <1> loc_mkdir_y_n_escape:
  3102 00009082 B04E                <1> 	mov	al, 'N' ; 'no'
  3103 00009084 EBCD                <1> 	jmp	short loc_do_not_make_directory
  3104                              <1> 
  3105                              <1> y_n_answer:
  3106                              <1> 	; 29/12/2017
  3107 00009086 A2[55170100]        <1> 	mov	[Y_N_nextline], al
  3108                              <1> 	;push	ax
  3109 0000908B 50                  <1> 	push	eax
  3110 0000908C BE[55170100]        <1> 	mov	esi, Y_N_nextline
  3111 00009091 E86FDBFFFF          <1> 	call	print_msg
  3112 00009096 58                  <1> 	pop	eax
  3113                              <1> 	;pop	ax
  3114 00009097 C3                  <1> 	retn
  3115                              <1> 
  3116                              <1> delete_directory:
  3117                              <1> 	; 29/12/2017
  3118                              <1> 	; 15/10/2016
  3119                              <1> 	; 01/03/2016, 06/03/2016
  3120                              <1> 	; 27/02/2016, 28/02/2016, 29/02/2016
  3121                              <1> 	; 26/02/2016 (TRDOS 386 = TRDOS v2.0)
  3122                              <1> 	; 16/10/2010 (CMD_INTR.ASM, 'cmp_cmd_rmdir')
  3123                              <1> 	; 05/06/2010
  3124                              <1> 	;
  3125                              <1> get_fchar:
  3126                              <1> 	; esi = directory name
  3127 00009098 803E20              <1> 	cmp	byte [esi], 20h
  3128 0000909B 7701                <1>         ja	short loc_rmdir_parse_path_name
  3129                              <1> 
  3130                              <1> loc_rmdir_nodirname_retn:
  3131 0000909D C3                  <1> 	retn
  3132                              <1> 
  3133                              <1> loc_rmdir_parse_path_name:
  3134 0000909E BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  3135 000090A3 E8481C0000          <1> 	call	parse_path_name
  3136 000090A8 0F8261F5FFFF        <1> 	jc	loc_cmd_failed
  3137                              <1> 
  3138                              <1> loc_rmdir_check_dirname_exists:
  3139 000090AE BE[28680100]        <1> 	mov	esi, FindFile_Name
  3140 000090B3 803E20              <1> 	cmp	byte [esi], 20h
  3141 000090B6 0F8653F5FFFF        <1> 	jna	loc_cmd_failed
  3142 000090BC 8935[A4680100]      <1> 	mov	[DelFile_FNPointer], esi 
  3143                              <1> 
  3144                              <1> loc_rmdir_drv:
  3145 000090C2 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  3146 000090C8 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  3147                              <1> 
  3148 000090CE 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  3149 000090D4 38F2                <1> 	cmp	dl, dh
  3150 000090D6 740B                <1> 	je	short loc_rmdir_change_directory
  3151                              <1> 
  3152 000090D8 E89FE6FFFF          <1> 	call	change_current_drive
  3153 000090DD 0F826AFEFFFF        <1> 	jc	loc_file_rw_cmd_failed
  3154                              <1> 
  3155                              <1> loc_rmdir_change_directory:
  3156 000090E3 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  3157 000090EA 7614                <1> 	jna	short loc_rmdir_find_directory
  3158                              <1> 
  3159 000090EC FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3160 000090F2 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  3161 000090F7 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  3162 000090F9 E8DC150000          <1> 	call	change_current_directory
  3163 000090FE 7211                <1> 	jc	short loc_rmdir_check_error_code
  3164                              <1> 
  3165                              <1> ;loc_rmdir_change_prompt_dir_string:
  3166                              <1> 	;call	change_prompt_dir_string
  3167                              <1> 
  3168                              <1> loc_rmdir_find_directory:
  3169                              <1> 	;mov	esi, FindFile_Name
  3170 00009100 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3171 00009106 66B81008            <1> 	mov	ax, 0810h ; Only directories
  3172 0000910A E810FAFFFF          <1> 	call	find_first_file
  3173 0000910F 730A                <1> 	jnc	short loc_rmdir_ambgfn_check
  3174                              <1> 
  3175                              <1> loc_rmdir_check_error_code:
  3176 00009111 3C02                <1> 	cmp	al, 2
  3177 00009113 740B                <1> 	je	short loc_rmdir_directory_not_found
  3178 00009115 F9                  <1> 	stc
  3179 00009116 E932FEFFFF          <1> 	jmp	loc_file_rw_cmd_failed
  3180                              <1> 
  3181                              <1> loc_rmdir_ambgfn_check:
  3182 0000911B 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  3183 0000911E 740F                <1> 	jz	short loc_rmdir_directory_found
  3184                              <1> 
  3185                              <1> loc_rmdir_directory_not_found:
  3186 00009120 BE[C9150100]        <1> 	mov	esi, Msg_Dir_Not_Found
  3187 00009125 E8DBDAFFFF          <1> 	call	print_msg
  3188                              <1> 
  3189 0000912A E91EFEFFFF          <1> 	jmp	loc_file_rw_restore_retn
  3190                              <1> 
  3191                              <1> loc_rmdir_directory_found:
  3192 0000912F 80E307              <1> 	and	bl, 07h ; Attributes
  3193 00009132 0F851FFEFFFF        <1> 	jnz	loc_permission_denied
  3194                              <1> 
  3195                              <1> loc_rmdir_save_lnel: ; 28/02/2016
  3196                              <1>        ;mov	bh, [LongName_EntryLength]
  3197 00009138 883D[AE680100]      <1> 	mov	[DelFile_LNEL], bh ; Long name entry length (if > 0)
  3198                              <1> 	; edi = Directory Entry Offset (DirBuff)
  3199                              <1> 	; esi = Directory Entry (FFF Structure)
  3200                              <1> 	;mov	[DelFile_DirEntryAddr], edi ; not required
  3201                              <1> 	;mov	ax, [edi+20] ; First Cluster High Word
  3202                              <1>         ;shl	eax, 16
  3203                              <1> 	;mov	ax, [edi+26] ; First Cluster Low Word
  3204                              <1> 	; ROOT Dir First Cluster = 0
  3205                              <1>         ;cmp	eax, 2
  3206                              <1> 	;jb	loc_update_direntry_1
  3207                              <1> 
  3208                              <1> pass_rmdir_fc_check:
  3209 0000913E 57                  <1> 	push	edi ; * (29/02/2016)
  3210                              <1> 
  3211 0000913F BE[5F170100]        <1> 	mov	esi, Msg_DoYouWantRmDir
  3212 00009144 E8BCDAFFFF          <1> 	call	print_msg
  3213 00009149 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3214 0000914F E8B1DAFFFF          <1> 	call	print_msg
  3215 00009154 BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  3216 00009159 E8A7DAFFFF          <1> 	call	print_msg
  3217                              <1> 
  3218                              <1> loc_rmdir_ask_again:
  3219 0000915E 30E4                <1> 	xor	ah, ah
  3220 00009160 E8F57CFFFF          <1> 	call	int16h
  3221 00009165 3C1B                <1> 	cmp	al, 1Bh
  3222                              <1> 	;je	short loc_do_not_delete_directory
  3223 00009167 7433                <1>         je      loc_rmdir_y_n_escape ; 06/03/2016
  3224 00009169 24DF                <1> 	and	al, 0DFh
  3225 0000916B A2[55170100]        <1> 	mov	[Y_N_nextline], al
  3226 00009170 3C59                <1> 	cmp	al, 'Y'
  3227 00009172 7404                <1> 	je	short loc_rmdir_yes_delete_directory
  3228 00009174 3C4E                <1> 	cmp	al, 'N'
  3229 00009176 75E6                <1> 	jne	short loc_rmdir_ask_again
  3230                              <1> 
  3231                              <1> loc_do_not_delete_directory:
  3232                              <1> loc_rmdir_yes_delete_directory:
  3233 00009178 E809FFFFFF          <1> 	call	y_n_answer ; 29/12/2017
  3234 0000917D 5F                  <1> 	pop	edi ; * (29/02/2016)
  3235                              <1> 	;cmp	al, 'Y' ; 'yes'
  3236                              <1> 	;cmc
  3237                              <1>         ;jnc	loc_file_rw_restore_retn
  3238 0000917E 3C4E                <1> 	cmp	al, 'N' ; 'no'
  3239 00009180 0F84C7FDFFFF        <1>         je	loc_file_rw_restore_retn 
  3240                              <1> 
  3241                              <1> 	; 29/12/2017
  3242 00009186 E869000000          <1> 	call	delete_sub_directory
  3243 0000918B 7213                <1> 	jc	short loc_rmdir_cmd_failed
  3244                              <1> 
  3245                              <1> loc_rmdir_ok:
  3246 0000918D BE[59170100]        <1> 	mov	esi, Msg_OK
  3247 00009192 E86EDAFFFF          <1> 	call	print_msg
  3248 00009197 E9B1FDFFFF          <1> 	jmp	loc_file_rw_restore_retn
  3249                              <1> 
  3250                              <1> loc_rmdir_y_n_escape:
  3251 0000919C B04E                <1> 	mov	al, 'N' ; 'no'
  3252 0000919E EBD8                <1>         jmp     loc_do_not_delete_directory
  3253                              <1> 
  3254                              <1> loc_rmdir_cmd_failed:
  3255                              <1> 	; 29/12/2017
  3256 000091A0 09C0                <1> 	or	eax, eax ; EAX = 0 -> Directory not empty!
  3257 000091A2 7426                <1> 	jz	short loc_rmdir_directory_not_empty
  3258                              <1> 
  3259                              <1> 	; EAX > 0 -> Error code in AL (or AX or EAX)
  3260                              <1> 
  3261 000091A4 833D[62660100]01    <1> 	cmp	dword [FAT_ClusterCounter], 1
  3262 000091AB 0F829CFDFFFF        <1> 	jb	loc_file_rw_cmd_failed	
  3263 000091B1 F9                  <1> 	stc
  3264                              <1> loc_rmdir_cmd_return:
  3265                              <1> 	; 01/03/2016
  3266 000091B2 9C                  <1> 	pushf
  3267                              <1> 	; ESI = Logical DOS Drive Description Table address	
  3268 000091B3 66BB00FF            <1> 	mov	bx, 0FF00h ; BH = FFh -> use ESI for Drive parameters
  3269                              <1> 	           ; BL = 0 -> Recalculate free cluster count
  3270 000091B7 50                  <1> 	push	eax
  3271 000091B8 E8C3380000          <1> 	call	calculate_fat_freespace	
  3272 000091BD 58                  <1> 	pop	eax
  3273 000091BE 9D                  <1> 	popf
  3274 000091BF 0F8288FDFFFF        <1> 	jc	loc_file_rw_cmd_failed
  3275 000091C5 E983FDFFFF          <1> 	jmp	loc_file_rw_restore_retn
  3276                              <1> 
  3277                              <1> loc_rmdir_directory_not_empty:
  3278 000091CA BE[80170100]        <1> 	mov	esi, Msg_Dir_Not_Empty
  3279 000091CF E831DAFFFF          <1> 	call	print_msg
  3280                              <1> 	; 01/03/2016
  3281 000091D4 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  3282 000091D9 09C0                <1> 	or	eax, eax ; 0 ?
  3283 000091DB 0F846CFDFFFF        <1> 	jz	loc_file_rw_restore_retn
  3284                              <1> 	; ESI = Logical DOS Drive Description Table address	
  3285 000091E1 66BB01FF            <1> 	mov	bx, 0FF01h ; BH = FFh -> use ESI for Drive parameters
  3286                              <1> 	           ; BL = 1 -> add free clusters
  3287 000091E5 E896380000          <1> 	call	calculate_fat_freespace
  3288 000091EA 09C9                <1> 	or	ecx, ecx
  3289 000091EC 0F845BFDFFFF        <1>         jz      loc_file_rw_restore_retn ; ecx = 0 -> OK
  3290                              <1> 	; ecx > 0 -> Error (Recalculation is needed)
  3291 000091F2 EBBE                <1> 	jmp	short loc_rmdir_cmd_return
  3292                              <1> 
  3293                              <1> 
  3294                              <1> delete_sub_directory:
  3295                              <1> 	; 29/12/2017 
  3296                              <1> 	; (moved here from 'delete_directory' for 'sysrmdir' )
  3297                              <1> 
  3298                              <1> 	; EDI = Directory buffer entry offset/address
  3299                              <1> 
  3300                              <1> loc_rmdir_delete_short_name_check_dir_empty:
  3301 000091F4 668B4714            <1> 	mov	ax, [edi+20] ; First Cluster High Word
  3302 000091F8 C1E010              <1>         shl	eax, 16
  3303 000091FB 668B471A            <1> 	mov	ax, [edi+26] ; First Cluster Low Word
  3304                              <1> 
  3305                              <1> 	;mov 	[DelFile_FCluster], eax
  3306                              <1> 
  3307                              <1> 	;;mov	bx, [DirBuff_EntryCounter]
  3308                              <1> 	;mov	bx, [FindFile_DirEntryNumber] ; 27/02/2016
  3309                              <1> 	;mov	[DelFile_EntryCounter], bx
  3310                              <1> 
  3311 000091FF 29DB                <1>     	sub	ebx, ebx
  3312                              <1> 	; 29/12/2017
  3313 00009201 891D[62660100]      <1> 	mov	[FAT_ClusterCounter], ebx ; 0 ; Reset
  3314                              <1> 
  3315 00009207 8A3D[E6670100]      <1> 	mov	bh, [FindFile_Drv]
  3316 0000920D BE00010900          <1> 	mov	esi, Logical_DOSDisks
  3317 00009212 01DE                <1> 	add	esi, ebx
  3318                              <1> 
  3319 00009214 66817F0CA101        <1> 	cmp	word [edi+DirEntry_NTRes], 01A1h
  3320 0000921A 745A                <1> 	je	short loc_rmdir_check_fs_directory
  3321                              <1> 
  3322                              <1> 	;cmp	byte [esi+LD_FATType], 1
  3323                              <1> 	;jb	short loc_rmdir_get__last_cluster_0
  3324                              <1> 
  3325                              <1> 	; 29/12/2017
  3326 0000921C 83F802              <1> 	cmp	eax, 2
  3327 0000921F 7306                <1> 	jnb	short loc_rmdir_get_last_cluster_1
  3328                              <1> 	; eax < 2
  3329                              <1> loc_rmdir_get_last_cluster_0:
  3330                              <1> 	;mov	eax, ERR_INV_FORMAT ; invalid format!
  3331 00009221 B813000000          <1> 	mov	eax, ERR_NOT_DIR ; not a valid directory!
  3332                              <1> 	;stc
  3333 00009226 C3                  <1> 	retn
  3334                              <1> 
  3335                              <1> loc_rmdir_get_last_cluster_1:
  3336 00009227 807E0303            <1> 	cmp	byte [esi+LD_FATType], 3 ; FAT32
  3337 0000922B 750C                <1> 	jne	short loc_rmdir_get_last_cluster_2
  3338                              <1> 
  3339                              <1> 	; is it root directory ?
  3340 0000922D 3B4632              <1> 	cmp	eax, [esi+LD_BPB+BPB_RootClus]
  3341 00009230 7507                <1> 	jne	short loc_rmdir_get_last_cluster_2
  3342                              <1> 
  3343                              <1> 	; root directory can not be deleted !!
  3344                              <1> loc_rmdir_permission_denied:
  3345 00009232 B80B000000          <1> 	mov	eax, ERR_PERM_DENIED ; permission denied!
  3346 00009237 F9                  <1> 	stc
  3347 00009238 C3                  <1> 	retn		
  3348                              <1> 
  3349                              <1> loc_rmdir_get_last_cluster_2:
  3350                              <1> 	; 29/12/2017
  3351 00009239 A3[A8680100]        <1> 	mov 	[DelFile_FCluster], eax
  3352                              <1> 	
  3353                              <1> 	;mov	dx, [DirBuff_EntryCounter]
  3354 0000923E 668B15[60680100]    <1> 	mov	dx, [FindFile_DirEntryNumber] ; 27/02/2016
  3355 00009245 668915[AC680100]    <1> 	mov	[DelFile_EntryCounter], dx
  3356                              <1> 	
  3357 0000924C 8B15[71660100]      <1> 	mov	edx, [DirBuff_Cluster]
  3358 00009252 8915[D8680100]      <1> 	mov	[RmDir_ParentDirCluster], edx
  3359                              <1> 
  3360 00009258 893D[D4680100]      <1> 	mov	[RmDir_DirEntryOffset], edi
  3361                              <1> 
  3362                              <1> 	; 01/03/2016
  3363                              <1> 	;mov	dword [FAT_ClusterCounter], 0 ; Reset
  3364                              <1> 
  3365                              <1> loc_rmdir_get_last_cluster_3:
  3366 0000925E E89C390000          <1> 	call	get_last_cluster
  3367                              <1>         ;jc	loc_rmdir_cmd_failed
  3368 00009263 721E                <1> 	jc	short loc_delete_sub_dir_retn ; 29/12/2017
  3369                              <1> 	
  3370 00009265 3B05[A8680100]      <1> 	cmp	eax, [DelFile_FCluster]
  3371 0000926B 7517                <1> 	jne	short loc_rmdir_multi_dir_clusters
  3372                              <1> 
  3373 0000926D C605[D3680100]00    <1> 	mov	byte [RmDir_MultiClusters], 0
  3374 00009274 EB15                <1> 	jmp	short pass_rmdir_multi_dir_clusters
  3375                              <1> 
  3376                              <1> loc_rmdir_check_fs_directory:
  3377                              <1> 	; 29/12/2017
  3378 00009276 807E04A1            <1> 	cmp	byte [esi+LD_FSType], 0A1h
  3379 0000927A 75B6                <1> 	jne	short loc_rmdir_permission_denied
  3380                              <1> 
  3381                              <1> loc_rmdir_delete_fs_directory:
  3382 0000927C E876130000          <1> 	call	delete_fs_directory
  3383                              <1> 	;jnc	loc_print_deleted_message
  3384 00009281 7300                <1> 	jnc	short loc_delete_sub_dir_retn ; 29/12/2017
  3385                              <1> 
  3386                              <1> 	; EAX=0 -> Directory not empty !
  3387                              <1> 	; EAX>0 -> Disk r/w error or another (misc) error
  3388                              <1> 	
  3389                              <1> 	;or	eax, eax
  3390                              <1> 	;jz	loc_rmdir_directory_not_empty_2         
  3391                              <1> 	;;stc
  3392                              <1> 	;;jmp	loc_file_rw_cmd_failed
  3393                              <1> 	
  3394                              <1> loc_delete_sub_dir_retn:
  3395 00009283 C3                  <1> 	retn
  3396                              <1>  
  3397                              <1> loc_rmdir_multi_dir_clusters:
  3398 00009284 C605[D3680100]01    <1> 	mov	byte [RmDir_MultiClusters], 1
  3399                              <1> 
  3400                              <1> pass_rmdir_multi_dir_clusters:
  3401 0000928B A3[DC680100]        <1> 	mov 	[RmDir_DirLastCluster], eax
  3402 00009290 890D[E0680100]      <1> 	mov	[RmDir_PreviousCluster], ecx
  3403                              <1> 
  3404                              <1> loc_rmdir_load_fat_sub_directory:
  3405 00009296 E84F330000          <1> 	call	load_FAT_sub_directory
  3406                              <1> 	;jc	loc_rmdir_cmd_failed
  3407 0000929B 72E6                <1> 	jc	short loc_delete_sub_dir_retn
  3408                              <1> 
  3409                              <1> loc_rmdir_find_last_dir_entry:
  3410 0000929D 56                  <1> 	push	esi
  3411 0000929E BE[CA670100]        <1> 	mov	esi, Dir_File_Name
  3412 000092A3 C6062A              <1> 	mov	byte [esi], '*'
  3413 000092A6 C646082A            <1> 	mov	byte [esi+8], '*'
  3414 000092AA 31DB                <1> 	xor	ebx, ebx ; Entry offset  = 0
  3415                              <1> loc_rmdir_find_last_dir_entry_next:
  3416 000092AC 66B80008            <1> 	mov	ax, 0800h ; Except volume/long names
  3417 000092B0 6631C9              <1> 	xor	cx, cx ; 0 = Find a valid file or dir name
  3418 000092B3 E87A170000          <1> 	call	find_directory_entry
  3419 000092B8 7225                <1> 	jc	short loc_rmdir_empty_dir_cluster
  3420 000092BA 83FB01              <1> 	cmp	ebx, 1
  3421 000092BD 771B                <1> 	ja	short loc_rmdir_directory_not_empty_1
  3422                              <1> loc_rmdir_dot_entry_check:
  3423 000092BF 80FD2E              <1> 	cmp	ch, '.' ; The first char of the dir entry
  3424 000092C2 7516                <1> 	jne	short loc_rmdir_directory_not_empty_1
  3425 000092C4 08DB                <1> 	or	bl, bl
  3426 000092C6 7506                <1> 	jnz	short loc_rmdir_dotdot_entry_check
  3427 000092C8 807F0120            <1> 	cmp	byte [edi+1], 20h
  3428 000092CC EB06                <1> 	jmp	short pass_rmdir_dot_entry_check
  3429                              <1> 
  3430                              <1> loc_rmdir_dotdot_entry_check:
  3431 000092CE 66817F012E20        <1> 	cmp	word [edi+1], '. '
  3432                              <1> pass_rmdir_dot_entry_check:	
  3433 000092D4 7504                <1> 	jne	short loc_rmdir_directory_not_empty_1 
  3434 000092D6 FEC3                <1> 	inc	bl
  3435 000092D8 EBD2                <1> 	jmp	short loc_rmdir_find_last_dir_entry_next 
  3436                              <1> 
  3437                              <1> loc_rmdir_directory_not_empty_1:
  3438 000092DA 58                  <1> 	pop	eax ; pushed esi 
  3439 000092DB 31C0                <1> 	xor	eax, eax ; 0
  3440                              <1> loc_rmdir_directory_not_empty_2:
  3441                              <1> loc_delete_sub_dir_stc_retn:
  3442 000092DD F9                  <1> 	stc
  3443 000092DE C3                  <1> 	retn
  3444                              <1> 
  3445                              <1> loc_rmdir_empty_dir_cluster:
  3446 000092DF 5E                  <1> 	pop	esi
  3447                              <1> 
  3448                              <1> loc_rmdir_set_prev_cluster_dir_last_cluster:
  3449 000092E0 803D[D3680100]00    <1> 	cmp	byte [RmDir_MultiClusters], 0
  3450 000092E7 7613                <1> 	jna	short loc_rmdir_unlink_dir_last_cluster
  3451                              <1> 
  3452 000092E9 A1[E0680100]        <1> 	mov	eax, [RmDir_PreviousCluster]
  3453                              <1> 	;xor	ecx, ecx
  3454 000092EE 49                  <1> 	dec	ecx ; FFFFFFFFh
  3455 000092EF E83A340000          <1> 	call	update_cluster
  3456 000092F4 7306                <1> 	jnc	short loc_rmdir_unlink_dir_last_cluster
  3457                              <1> 
  3458                              <1> 	; 01/03/2016
  3459                              <1> 	;cmp	eax, 1  ; eax = 0 -> end of cluster chain
  3460                              <1> 	;cmc 
  3461                              <1> 	;jc	short loc_rmdir_cmd_failed
  3462                              <1> 	;jmp	short loc_rmdir_save_fat_buffer
  3463                              <1> 	; 29/12/2017 
  3464 000092F6 21C0                <1> 	and	eax, eax
  3465 000092F8 75E3                <1> 	jnz	short loc_delete_sub_dir_stc_retn
  3466 000092FA EB12                <1> 	jmp	short loc_rmdir_save_fat_buffer	
  3467                              <1> 
  3468                              <1> loc_rmdir_unlink_dir_last_cluster:
  3469 000092FC A1[DC680100]        <1> 	mov	eax, [RmDir_DirLastCluster]
  3470 00009301 31C9                <1> 	xor	ecx, ecx ; 0
  3471 00009303 E826340000          <1> 	call	update_cluster
  3472 00009308 7327                <1> 	jnc	short loc_rmdir_unlink_stc_retn_0Bh
  3473                              <1> 	; Because of it is the last cluster
  3474                              <1> 	; 'update_cluster' must return with eocc error 
  3475 0000930A 09C0                <1> 	or	eax, eax
  3476                              <1> 	;jz	short loc_rmdir_save_fat_buffer ; eocc	
  3477                              <1> 	;stc
  3478                              <1>         ;jmp     short loc_rmdir_cmd_failed
  3479                              <1> 	; 29/12/2017
  3480 0000930C 75CF                <1> 	jnz	short loc_delete_sub_dir_stc_retn
  3481                              <1> 	
  3482                              <1> loc_rmdir_save_fat_buffer:
  3483 0000930E 803D[5A660100]02    <1> 	cmp	byte [FAT_BuffValidData], 2
  3484 00009315 7528                <1> 	jne	short loc_rmdir_calculate_FAT_freespace
  3485 00009317 E8CF360000          <1> 	call	save_fat_buffer
  3486                              <1> 	;jc	short loc_rmdir_cmd_failed
  3487                              <1> 	; 29/12/2017
  3488 0000931C 7219                <1> 	jc	short loc_rmdir_unlink_error_retn
  3489                              <1> 
  3490                              <1> 	; 01/03/2016
  3491 0000931E 803D[D3680100]00    <1> 	cmp	byte [RmDir_MultiClusters], 0
  3492 00009325 7618                <1> 	jna	short loc_rmdir_calculate_FAT_freespace
  3493                              <1> 
  3494 00009327 A1[A8680100]        <1> 	mov	eax, [DelFile_FCluster]
  3495 0000932C E92DFFFFFF          <1>         jmp     loc_rmdir_get_last_cluster_3
  3496                              <1> 
  3497                              <1> loc_rmdir_unlink_stc_retn_0Bh:
  3498                              <1> 	; 15/10/2016 (0Bh -> 28)
  3499 00009331 B81C000000          <1> 	mov	eax, ERR_INV_FORMAT ; 28 = Invalid format
  3500                              <1> loc_rmdir_unlink_stc_retn:
  3501 00009336 F9                  <1> 	stc
  3502                              <1> loc_rmdir_unlink_error_retn:
  3503 00009337 C3                  <1> 	retn
  3504                              <1> 
  3505                              <1> loc_rmdir_delete_short_name_invalid_data:
  3506 00009338 B81D000000          <1> 	mov	eax, 29 ; Invalid data (15/10/2016)
  3507                              <1> 	;stc
  3508                              <1>         ;jmp	loc_rmdir_cmd_failed
  3509                              <1> 	; 29/12/2017
  3510 0000933D EBF7                <1> 	jmp	short loc_rmdir_unlink_stc_retn
  3511                              <1> 
  3512                              <1> loc_rmdir_calculate_FAT_freespace:
  3513                              <1> 	;mov	eax, [FAT_ClusterCounter]
  3514                              <1> 	; 29/12/2017
  3515 0000933F 29C0                <1> 	sub	eax, eax ; 0
  3516 00009341 8705[62660100]      <1> 	xchg	eax, [FAT_ClusterCounter]
  3517                              <1> 	;
  3518 00009347 66BB01FF            <1> 	mov	bx, 0FF01h
  3519                              <1> 	; BL = 1 -> Add EAX to free space count
  3520                              <1> 	; BH = FFh ->
  3521                              <1> 	; ESI = Logical DOS Drive Description Table address
  3522 0000934B E830370000          <1> 	call	calculate_fat_freespace
  3523                              <1> 
  3524 00009350 21C9                <1> 	and	ecx, ecx ; ecx = 0 -> valid free sector count
  3525 00009352 7409                <1> 	jz 	short loc_rmdir_delete_short_name_continue
  3526                              <1> 
  3527                              <1> loc_rmdir_recalculate_FAT_freespace:
  3528 00009354 66BB00FF            <1>         mov     bx, 0FF00h ; BL = 0 -> Recalculate free space
  3529 00009358 E823370000          <1> 	call	calculate_fat_freespace
  3530                              <1> 	          
  3531                              <1> loc_rmdir_delete_short_name_continue:
  3532 0000935D A1[D8680100]        <1> 	mov	eax, [RmDir_ParentDirCluster]
  3533 00009362 83F802              <1> 	cmp	eax, 2
  3534 00009365 7309                <1> 	jnb	short loc_rmdir_del_short_name_load_sub_dir
  3535 00009367 E8F3310000          <1> 	call	load_FAT_root_directory
  3536                              <1> 	;jc	loc_file_rw_cmd_failed
  3537                              <1> 	; 29/12/2017
  3538 0000936C 72C9                <1> 	jc	short loc_rmdir_unlink_error_retn
  3539 0000936E EB07                <1> 	jmp	short loc_rmdir_del_short_name_ld_chk_fclust
  3540                              <1> 
  3541                              <1> loc_rmdir_del_short_name_load_sub_dir:	
  3542 00009370 E875320000          <1> 	call	load_FAT_sub_directory
  3543                              <1> 	;jc	loc_file_rw_cmd_failed
  3544                              <1> 	; 29/12/2017
  3545 00009375 72C0                <1> 	jc	short loc_rmdir_unlink_error_retn
  3546                              <1> 
  3547                              <1> loc_rmdir_del_short_name_ld_chk_fclust:
  3548 00009377 0FB73D[D4680100]    <1> 	movzx	edi, word [RmDir_DirEntryOffset]
  3549 0000937E 81C700000800        <1> 	add	edi, Directory_Buffer
  3550                              <1> 
  3551 00009384 668B4714            <1> 	mov	ax, [edi+20] ; First Cluster High Word
  3552 00009388 C1E010              <1> 	shl	eax, 16
  3553 0000938B 668B471A            <1> 	mov	ax, [edi+26] ; First Cluster Low Word
  3554                              <1>         ; Not necessary... 
  3555 0000938F 3B05[A8680100]      <1> 	cmp	eax, [DelFile_FCluster]
  3556 00009395 75A1                <1> 	jne	short loc_rmdir_delete_short_name_invalid_data
  3557                              <1> 	;
  3558 00009397 C607E5              <1> 	mov	byte [edi], 0E5h ; 'Deleted' sign
  3559                              <1> 	; 27/02/2016
  3560                              <1> 	; TRDOS v1 has a bug here! it does not set
  3561                              <1> 	; 'DirBuff_ValidData' to 2; as result of this bug,
  3562                              <1> 	; 'save_directory_buffer' would not save the change ! 
  3563 0000939A C605[6C660100]02    <1>   	mov	byte [DirBuff_ValidData], 2 ; change sign
  3564                              <1> 	;
  3565 000093A1 E8AE1D0000          <1> 	call	save_directory_buffer
  3566                              <1> 	;jc	loc_file_rw_cmd_failed
  3567                              <1> 	; 29/12/2017
  3568 000093A6 728F                <1> 	jc	short loc_rmdir_unlink_error_retn
  3569                              <1> 
  3570                              <1> loc_rmdir_del_long_name:
  3571 000093A8 0FB615[AE680100]    <1> 	movzx	edx, byte [DelFile_LNEL]
  3572 000093AF 08D2                <1> 	or	dl, dl
  3573 000093B1 7410                <1> 	jz	short loc_rmdir_update_parent_dir_lmdt
  3574                              <1>              
  3575 000093B3 0FB705[AC680100]    <1> 	movzx	eax, word [DelFile_EntryCounter]
  3576 000093BA 29D0                <1> 	sub	eax, edx
  3577                              <1> 	; 29/12/2017
  3578 000093BC 7205                <1> 	jc	short loc_rmdir_update_parent_dir_lmdt
  3579                              <1>  
  3580                              <1>  	; EAX = Directory Entry Number of the long name last entry
  3581 000093BE E8EF1E0000          <1> 	call	delete_longname
  3582                              <1> 
  3583                              <1> loc_rmdir_update_parent_dir_lmdt:
  3584 000093C3 E8271E0000          <1> 	call	update_parent_dir_lmdt
  3585                              <1> 	;jc	short loc_file_rw_cmd_failed
  3586                              <1> 	; 29/12/2017
  3587                              <1> 	;jc	short loc_rmdir_unlink_error_retn
  3588                              <1> 
  3589                              <1> loc_delete_sub_directory_ok:
  3590                              <1> 	; 29/12/2017
  3591 000093C8 31C0                <1> 	xor	eax, eax ;  0 ;  cf = 0
  3592 000093CA C3                  <1> 	retn
  3593                              <1> 
  3594                              <1> 
  3595                              <1> delete_file:
  3596                              <1> 	; 29/02/2016
  3597                              <1> 	; 28/02/2016 (TRDOS 386 = TRDOS v2.0)
  3598                              <1> 	; 09/08/2010 (CMD_INTR.ASM, 'cmp_cmd_del')
  3599                              <1> 	; 28/02/2010
  3600                              <1> 
  3601                              <1> get_delfile_fchar:
  3602                              <1> 	; esi = file name
  3603 000093CB 803E20              <1> 	cmp	byte [esi], 20h
  3604 000093CE 7701                <1>         ja	short loc_delfile_parse_path_name
  3605                              <1> 
  3606                              <1> loc_delfile_nofilename_retn:
  3607 000093D0 C3                  <1> 	retn
  3608                              <1> 
  3609                              <1> loc_delfile_parse_path_name:
  3610 000093D1 BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  3611 000093D6 E815190000          <1> 	call	parse_path_name
  3612 000093DB 0F822EF2FFFF        <1> 	jc	loc_cmd_failed
  3613                              <1> 
  3614                              <1> loc_delfile_check_filename_exists:
  3615 000093E1 BE[28680100]        <1> 	mov	esi, FindFile_Name
  3616 000093E6 803E20              <1> 	cmp	byte [esi], 20h
  3617 000093E9 0F8620F2FFFF        <1> 	jna	loc_cmd_failed
  3618 000093EF 8935[A4680100]      <1> 	mov	[DelFile_FNPointer], esi 
  3619                              <1> 
  3620                              <1> loc_delfile_drv:
  3621 000093F5 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  3622 000093FB 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  3623 00009401 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  3624 00009407 38F2                <1> 	cmp	dl, dh
  3625 00009409 740B                <1> 	je	short loc_delfile_change_directory
  3626                              <1> 
  3627 0000940B E86CE3FFFF          <1> 	call	change_current_drive
  3628 00009410 0F8237FBFFFF        <1> 	jc	loc_file_rw_cmd_failed
  3629                              <1> 
  3630                              <1> loc_delfile_change_directory:
  3631 00009416 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  3632 0000941D 7618                <1> 	jna	short loc_delfile_find
  3633                              <1> 
  3634 0000941F FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3635 00009425 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  3636 0000942A 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  3637 0000942C E8A9120000          <1> 	call	change_current_directory
  3638 00009431 0F8216FBFFFF        <1> 	jc	loc_file_rw_cmd_failed
  3639                              <1> 
  3640                              <1> ;loc_delfile_change_prompt_dir_string:
  3641                              <1> 	;call	change_prompt_dir_string
  3642                              <1> 
  3643                              <1> loc_delfile_find:
  3644                              <1> 	;mov	esi, FindFile_Name
  3645 00009437 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3646 0000943D 66B80018            <1> 	mov	ax, 1800h ; Except volume label and dirs
  3647 00009441 E8D9F6FFFF          <1> 	call	find_first_file
  3648 00009446 0F8201FBFFFF        <1> 	jc	loc_file_rw_cmd_failed
  3649                              <1> 
  3650                              <1> loc_delfile_ambgfn_check:
  3651 0000944C 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  3652 0000944F 740B                <1> 	jz	short loc_delfile_found
  3653                              <1> 
  3654                              <1> loc_file_not_found:
  3655 00009451 B802000000          <1> 	mov	eax, 2 ; File not found sign
  3656 00009456 F9                  <1> 	stc
  3657 00009457 E9F1FAFFFF          <1> 	jmp	loc_file_rw_cmd_failed   
  3658                              <1> 
  3659                              <1> loc_delfile_found:
  3660 0000945C 80E307              <1> 	and	bl, 07h ; Attributes
  3661 0000945F 0F85F2FAFFFF        <1>         jnz     loc_permission_denied
  3662                              <1> 
  3663                              <1> ;loc_delfile_found_save_lnel:
  3664                              <1> ;	mov	[DelFile_LNEL], bh ; Long name entry length (if > 0)
  3665                              <1> 
  3666                              <1> loc_delfile_ask_for_delete:
  3667 00009465 57                  <1> 	push	edi ; * (29/02/2016)
  3668                              <1> 
  3669 00009466 BE[97170100]        <1> 	mov	esi, Msg_DoYouWantDelete
  3670 0000946B E895D7FFFF          <1> 	call	print_msg
  3671 00009470 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3672 00009476 E88AD7FFFF          <1> 	call	print_msg
  3673 0000947B BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  3674 00009480 E880D7FFFF          <1> 	call	print_msg
  3675                              <1> 
  3676                              <1> loc_delfile_ask_again:
  3677 00009485 30E4                <1> 	xor	ah, ah
  3678 00009487 E8CE79FFFF          <1> 	call	int16h
  3679 0000948C 3C1B                <1> 	cmp	al, 1Bh
  3680                              <1> 	;je	short loc_do_not_delete_file
  3681 0000948E 7449                <1> 	je	short loc_delfile_y_n_escape ; 06/03/2016
  3682 00009490 24DF                <1> 	and	al, 0DFh
  3683 00009492 A2[55170100]        <1> 	mov	[Y_N_nextline], al
  3684 00009497 3C59                <1> 	cmp	al, 'Y'
  3685 00009499 7404                <1> 	je	short loc_yes_delete_file
  3686 0000949B 3C4E                <1> 	cmp	al, 'N'
  3687 0000949D 75E6                <1> 	jne	short loc_delfile_ask_again
  3688                              <1> 
  3689                              <1> loc_do_not_delete_file:
  3690                              <1> loc_yes_delete_file:
  3691 0000949F E8E2FBFFFF          <1> 	call	y_n_answer ; 29/12/2017
  3692 000094A4 5F                  <1> 	pop	edi ; * (29/02/2016)
  3693                              <1> 	;cmp	al, 'Y' ; 'yes'
  3694                              <1> 	;cmc
  3695                              <1>         ;jnc	loc_file_rw_restore_retn
  3696 000094A5 3C4E                <1> 	cmp	al, 'N' ; 'no'
  3697 000094A7 0F84A0FAFFFF        <1>         je	loc_file_rw_restore_retn  
  3698                              <1> 
  3699                              <1> loc_delete_file:
  3700 000094AD 8A3D[E6670100]      <1> 	mov	bh, [FindFile_Drv]
  3701                              <1> 	;mov	bl, [DelFile_LNEL]
  3702 000094B3 8A1D[35680100]      <1> 	mov	bl, [FindFile_LongNameEntryLength]
  3703                              <1> 	;mov	cx, [DirBuff_EntryCounter]
  3704 000094B9 668B0D[60680100]    <1> 	mov	cx, [FindFile_DirEntryNumber]
  3705                              <1> 	; (*) EDI = Directory buffer entry offset/address 
  3706 000094C0 E8D71F0000          <1> 	call	remove_file ; (FILE.ASM, 'proc_delete_file')
  3707 000094C5 0F8378FAFFFF        <1> 	jnc	loc_print_deleted_message
  3708                              <1> 
  3709                              <1> 	;cmp	al, 05h
  3710 000094CB 3C0B                <1> 	cmp	al, ERR_PERM_DENIED  ; 29/12/2017 (5 -> 11)
  3711 000094CD 0F8484FAFFFF        <1> 	je	loc_permission_denied
  3712 000094D3 F9                  <1> 	stc
  3713 000094D4 E974FAFFFF          <1> 	jmp	loc_file_rw_cmd_failed
  3714                              <1> 
  3715                              <1> loc_delfile_y_n_escape:
  3716 000094D9 B04E                <1> 	mov	al, 'N' ; 'no'
  3717 000094DB EBC2                <1> 	jmp	short loc_do_not_delete_file
  3718                              <1> 
  3719                              <1> set_file_attributes:
  3720                              <1> 	; 06/03/2016
  3721                              <1> 	; 04/03/2016 (TRDOS 386 = TRDOS v2.0)
  3722                              <1> 	; 10/07/2010 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_attrib')
  3723                              <1> 	; 23/05/2010 
  3724                              <1> 	; 17/12/2000 (P2000.ASM)
  3725                              <1> 
  3726                              <1> 	; esi = file or directory name
  3727 000094DD 6631C0              <1> 	xor	ax, ax
  3728 000094E0 66A3[E8170100]      <1> 	mov	[Attr_Chars], ax
  3729 000094E6 A2[FC680100]        <1> 	mov	[Attributes], al
  3730                              <1> 
  3731                              <1> get_attrib_fchar:
  3732                              <1> 	; esi = file name
  3733 000094EB 8A06                <1> 	mov	al, [esi]
  3734 000094ED 3C20                <1> 	cmp	al, 20h
  3735 000094EF 7623                <1> 	jna	short loc_attr_file_nofilename_retn
  3736                              <1> 
  3737                              <1> loc_scan_attrib_params:
  3738 000094F1 3C2D                <1> 	cmp	al, '-'
  3739 000094F3 0F871C010000        <1> 	ja	loc_attr_file_parse_path_name
  3740 000094F9 7408                <1> 	je	short loc_attr_space
  3741                              <1> 
  3742 000094FB 3C2B                <1> 	cmp	al, '+'
  3743 000094FD 0F850CF1FFFF        <1> 	jne	loc_cmd_failed
  3744                              <1> 
  3745                              <1> loc_attr_space:
  3746 00009503 8A6601              <1> 	mov	ah, [esi+1]
  3747 00009506 80FC20              <1>  	cmp	ah, 20h
  3748 00009509 770A                <1> 	ja	short pass_attr_space
  3749 0000950B 0F82FEF0FFFF        <1> 	jb	loc_cmd_failed
  3750 00009511 46                  <1> 	inc	esi
  3751 00009512 EBEF                <1> 	jmp	short loc_attr_space
  3752                              <1> 
  3753                              <1> loc_attr_file_nofilename_retn:
  3754 00009514 C3                  <1> 	retn
  3755                              <1> 
  3756                              <1> pass_attr_space:
  3757 00009515 80E4DF              <1> 	and	ah, 0DFh
  3758 00009518 80FC53              <1> 	cmp	ah, 'S'
  3759 0000951B 0F87EEF0FFFF        <1> 	ja	loc_cmd_failed
  3760 00009521 7204                <1> 	jb	short pass_attr_system
  3761 00009523 B404                <1> 	mov	ah, 04h   ; System
  3762 00009525 EB21                <1> 	jmp	short pass_attr_archive
  3763                              <1> 
  3764                              <1> pass_attr_system:
  3765 00009527 80FC48              <1> 	cmp	ah, 'H'
  3766 0000952A 7706                <1> 	ja	short pass_attr_hidden
  3767 0000952C 7213                <1> 	jb	short pass_attr_read_only
  3768 0000952E B402                <1> 	mov	ah, 02h    ; Hidden
  3769 00009530 EB16                <1> 	jmp	short pass_attr_archive
  3770                              <1> 
  3771                              <1> pass_attr_hidden:
  3772 00009532 80FC52              <1> 	cmp	ah, 'R'
  3773 00009535 0F87D4F0FFFF        <1> 	ja	loc_cmd_failed
  3774 0000953B 7204                <1> 	jb	short pass_attr_read_only ; Read only
  3775 0000953D B401                <1> 	mov	ah, 01h
  3776 0000953F EB07                <1> 	jmp	short pass_attr_archive
  3777                              <1> 
  3778                              <1> pass_attr_read_only:
  3779 00009541 80FC41              <1> 	cmp	ah, 'A'
  3780 00009544 753B                <1> 	jne	short loc_chk_attr_enter
  3781 00009546 B420                <1> 	mov	ah, 20h    ; Archive
  3782                              <1> 
  3783                              <1> pass_attr_archive:
  3784 00009548 3C2D                <1> 	cmp	al, '-'
  3785 0000954A 7508                <1> 	jne	short pass_reducing_attributes
  3786 0000954C 0825[E8170100]      <1> 	or	[Attr_Chars], ah
  3787 00009552 EB06                <1> 	jmp	short loc_change_attributes_inc
  3788                              <1> 
  3789                              <1> pass_reducing_attributes:
  3790 00009554 0825[E9170100]      <1> 	or	[Attr_Chars+1], ah
  3791                              <1> 
  3792                              <1> loc_change_attributes_inc:
  3793 0000955A 46                  <1> 	inc	esi
  3794 0000955B 8A6601              <1> 	mov	ah, [esi+1]
  3795 0000955E 80FC20              <1> 	cmp	ah, 20h
  3796 00009561 7227                <1> 	jb	short pass_change_attr
  3797 00009563 74F5                <1> 	je	short loc_change_attributes_inc
  3798 00009565 80FC2D              <1> 	cmp	ah, '-'
  3799 00009568 770D                <1> 	ja	short loc_chk_next_attr_char1
  3800 0000956A 7405                <1> 	je	short loc_chk_next_attr_char0
  3801 0000956C 80FC2B              <1> 	cmp	ah, '+'
  3802 0000956F 7506                <1> 	jne	short loc_chk_next_attr_char1
  3803                              <1> 
  3804                              <1> loc_chk_next_attr_char0:
  3805 00009571 46                  <1> 	inc	esi
  3806 00009572 668B06              <1> 	mov	ax, [esi]
  3807 00009575 EB9E                <1> 	jmp	short pass_attr_space
  3808                              <1> 
  3809                              <1> loc_chk_next_attr_char1:
  3810 00009577 803E2D              <1> 	cmp	byte [esi], '-'
  3811 0000957A 7799                <1> 	ja	short pass_attr_space
  3812 0000957C E988000000          <1>         jmp     loc_attr_file_check_fname_fchar
  3813                              <1> 
  3814                              <1> loc_chk_attr_enter:
  3815 00009581 80FC0D              <1> 	cmp	ah, 0Dh
  3816 00009584 0F8585F0FFFF        <1> 	jne	loc_cmd_failed
  3817                              <1> 
  3818                              <1> pass_change_attr:
  3819 0000958A A0[E8170100]        <1> 	mov	al, [Attr_Chars]
  3820 0000958F F6D0                <1> 	not	al
  3821 00009591 2005[FC680100]      <1> 	and	[Attributes], al
  3822 00009597 A0[E9170100]        <1> 	mov	al, [Attr_Chars+1]
  3823 0000959C 0805[FC680100]      <1> 	or	[Attributes], al
  3824                              <1> 
  3825                              <1> loc_show_attributes:
  3826 000095A2 BE[631F0100]        <1> 	mov	esi, nextline
  3827 000095A7 E859D6FFFF          <1> 	call	print_msg
  3828                              <1> 
  3829                              <1> loc_show_attributes_no_nextline:
  3830 000095AC C705[E8170100]4E4F- <1> 	mov	dword [Attr_Chars], 'NORM'
  3830 000095B4 524D                <1>
  3831 000095B6 66C705[EC170100]41- <1> 	mov	word [Attr_Chars+4], 'AL'
  3831 000095BE 4C                  <1>
  3832 000095BF BE[E8170100]        <1> 	mov	esi, Attr_Chars
  3833 000095C4 A0[FC680100]        <1> 	mov	al, [Attributes]
  3834 000095C9 A804                <1> 	test	al, 04h
  3835 000095CB 7406                <1> 	jz	short pass_put_attr_s
  3836 000095CD 66C7065300          <1> 	mov	word [esi], 0053h     ; S
  3837 000095D2 46                  <1> 	inc	esi
  3838                              <1> 
  3839                              <1> pass_put_attr_s:
  3840 000095D3 A802                <1> 	test	al, 02h
  3841 000095D5 7406                <1> 	jz	short pass_put_attr_h
  3842 000095D7 66C7064800          <1> 	mov	word [esi], 0048h     ; H
  3843 000095DC 46                  <1> 	inc	esi
  3844                              <1> 
  3845                              <1> pass_put_attr_h:
  3846 000095DD A801                <1> 	test	al, 01h
  3847 000095DF 7406                <1> 	jz	short pass_put_attr_r
  3848 000095E1 66C7065200          <1> 	mov	word [esi], 0052h     ; R
  3849 000095E6 46                  <1> 	inc	esi
  3850                              <1> 
  3851                              <1> pass_put_attr_r:
  3852 000095E7 3C20                <1> 	cmp	al, 20h
  3853 000095E9 7205                <1> 	jb	short pass_put_attr_a
  3854 000095EB 66C7064100          <1> 	mov	word [esi], 0041h     ; A
  3855                              <1> 
  3856                              <1> pass_put_attr_a:
  3857 000095F0 BE[DB170100]        <1> 	mov	esi, Str_Attributes
  3858 000095F5 E80BD6FFFF          <1> 	call	print_msg
  3859 000095FA BE[631F0100]        <1> 	mov	esi, nextline
  3860 000095FF E801D6FFFF          <1> 	call	print_msg
  3861 00009604 E944F9FFFF          <1> 	jmp	loc_file_rw_restore_retn 
  3862                              <1> 
  3863                              <1> loc_attr_file_check_fname_fchar:
  3864 00009609 46                  <1> 	inc	esi
  3865 0000960A 803E20              <1> 	cmp	byte [esi], 20h
  3866 0000960D 74FA                <1> 	je	short loc_attr_file_check_fname_fchar
  3867 0000960F 0F8275FFFFFF        <1>         jb      pass_change_attr
  3868                              <1> 		   
  3869                              <1> loc_attr_file_parse_path_name:
  3870 00009615 BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  3871 0000961A E8D1160000          <1> 	call	parse_path_name
  3872 0000961F 0F82EAEFFFFF        <1> 	jc	loc_cmd_failed
  3873                              <1> 
  3874                              <1> loc_attr_file_check_filename_exists:
  3875 00009625 BE[28680100]        <1> 	mov	esi, FindFile_Name
  3876 0000962A 803E20              <1> 	cmp	byte [esi], 20h
  3877 0000962D 0F86DCEFFFFF        <1> 	jna	loc_cmd_failed
  3878 00009633 8935[A4680100]      <1> 	mov	[DelFile_FNPointer], esi 
  3879                              <1> 
  3880                              <1> loc_attr_file_drv:
  3881 00009639 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  3882 0000963F 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  3883                              <1> 
  3884 00009645 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  3885 0000964B 38F2                <1> 	cmp	dl, dh
  3886 0000964D 740B                <1> 	je	short loc_attr_file_change_directory
  3887                              <1> 
  3888 0000964F E828E1FFFF          <1> 	call	change_current_drive
  3889 00009654 0F82F3F8FFFF        <1> 	jc	loc_file_rw_cmd_failed
  3890                              <1> 
  3891                              <1> loc_attr_file_change_directory:
  3892 0000965A 803D[E7670100]20    <1>         cmp     byte [FindFile_Directory], 20h
  3893 00009661 7618                <1> 	jna	short loc_attr_file_find
  3894                              <1> 
  3895 00009663 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3896                              <1> 	
  3897 00009669 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  3898 0000966E 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  3899 00009670 E865100000          <1> 	call	change_current_directory
  3900 00009675 0F82D2F8FFFF        <1> 	jc	loc_file_rw_cmd_failed
  3901                              <1> 
  3902                              <1> ;loc_attr_file_change_prompt_dir_string:
  3903                              <1> 	;call	change_prompt_dir_string
  3904                              <1> 
  3905                              <1> loc_attr_file_find:
  3906                              <1> 	;mov	esi, FindFile_Name
  3907 0000967B 8B35[A4680100]      <1> 	mov	esi, [DelFile_FNPointer]
  3908 00009681 66B80008            <1> 	mov	ax, 0800h ; Except volume labels
  3909 00009685 E895F4FFFF          <1> 	call	find_first_file
  3910 0000968A 0F82BDF8FFFF        <1> 	jc	loc_file_rw_cmd_failed
  3911                              <1> 
  3912                              <1> loc_attr_file_ambgfn_check:
  3913 00009690 6609D2              <1> 	or	dx, dx ; Ambiguous filename chars used sign (DX>0)
  3914                              <1> 	;	(Note: It was BX in TRDOS v1)
  3915                              <1> 	;jz	short loc_attr_file_found
  3916 00009693 0F85B8FDFFFF        <1>         jnz     loc_file_not_found ; 06/03/2016 
  3917                              <1> 
  3918                              <1> 	;mov	eax, 2 ; File not found sign
  3919                              <1> 	;stc
  3920                              <1> 	;jmp	loc_file_rw_cmd_failed   
  3921                              <1> 
  3922                              <1> loc_attr_file_found:
  3923                              <1> 	; EDI = Directory buffer entry offset/address
  3924                              <1> 	; BL = File (or Directory) Attributes 
  3925                              <1> 	;	(Note: It was 'CL' in TRDOS v1)
  3926                              <1> 	; mov	bl, [EDI+0Bh]
  3927                              <1> 	
  3928 00009699 66833D[E8170100]00  <1> 	cmp	word [Attr_Chars], 0
  3929 000096A1 770B                <1> 	ja	short loc_attr_file_change_attributes
  3930 000096A3 881D[FC680100]      <1> 	mov	[Attributes], bl
  3931 000096A9 E9F4FEFFFF          <1> 	jmp	loc_show_attributes
  3932                              <1> 
  3933                              <1> loc_attr_file_change_attributes:
  3934 000096AE A0[E8170100]        <1> 	mov	al, [Attr_Chars]
  3935 000096B3 F6D0                <1> 	not	al
  3936 000096B5 20C3                <1> 	and	bl, al
  3937 000096B7 A0[E9170100]        <1> 	mov	al, [Attr_Chars+1]
  3938 000096BC 08C3                <1> 	or	bl, al
  3939                              <1> 
  3940 000096BE 66817F0CA101        <1> 	cmp	word [edi+DirEntry_NTRes], 01A1h ; Singlix FS
  3941 000096C4 741D                <1> 	je	short loc_attr_file_fs_check
  3942                              <1> 
  3943 000096C6 881D[FC680100]      <1> 	mov	[Attributes], bl
  3944 000096CC 885F0B              <1> 	mov	[edi+0Bh], bl    ; Attributes (New!)
  3945                              <1> 
  3946                              <1> 	; 04/03/2016
  3947                              <1> 	; TRDOS v1 has a bug here! it does not set
  3948                              <1> 	; 'DirBuff_ValidData' to 2; as result of this bug,
  3949                              <1> 	; 'save_directory_buffer' would not save the new attributes ! 
  3950                              <1> 	
  3951 000096CF C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  3952                              <1> 
  3953 000096D6 E8791A0000          <1> 	call 	save_directory_buffer
  3954 000096DB 0F826CF8FFFF        <1> 	jc	loc_file_rw_cmd_failed
  3955                              <1> 
  3956 000096E1 EB33                <1> 	jmp	short loc_print_attr_changed_message
  3957                              <1> 
  3958                              <1> loc_attr_file_fs_check:
  3959 000096E3 29C0                <1> 	sub	eax, eax
  3960 000096E5 8A25[6A660100]      <1>         mov     ah, [DirBuff_DRV]
  3961 000096EB BE00010900          <1> 	mov	esi, Logical_DOSDisks
  3962 000096F0 01C6                <1>         add     esi, eax
  3963 000096F2 807E04A1            <1>         cmp     byte [esi+LD_FSType], 0A1h
  3964 000096F6 7309                <1> 	jnc	short loc_attr_file_change_fs_file_attributes
  3965                              <1> 	; 29/12/2017 (0Dh -> 29)	
  3966 000096F8 66B81D00            <1> 	mov	ax, 29 ; Invalid Data
  3967 000096FC E94CF8FFFF          <1> 	jmp	loc_file_rw_cmd_failed
  3968                              <1> 
  3969                              <1> loc_attr_file_change_fs_file_attributes:
  3970                              <1> 	; BL = New MS-DOS File Attributes
  3971 00009701 88D8                <1> 	mov	al, bl ; File/Directory Attributes
  3972 00009703 30E4                <1> 	xor	ah, ah ; Attributes in MS-DOS format sign	  
  3973 00009705 E873050000          <1> 	call	change_fs_file_attributes
  3974 0000970A 0F823DF8FFFF        <1> 	jc	loc_file_rw_cmd_failed
  3975                              <1> 
  3976 00009710 881D[FC680100]      <1> 	mov	[Attributes], bl 
  3977                              <1> 
  3978                              <1> loc_print_attr_changed_message:
  3979 00009716 BE[D6170100]        <1> 	mov	esi, Msg_New
  3980 0000971B E8E5D4FFFF          <1> 	call	print_msg
  3981 00009720 E987FEFFFF          <1> 	jmp	loc_show_attributes_no_nextline
  3982                              <1> 
  3983                              <1> rename_file:
  3984                              <1> 	; 13/11/2017
  3985                              <1> 	; 06/11/2016
  3986                              <1> 	; 05/11/2016
  3987                              <1> 	; 16/10/2016
  3988                              <1> 	; 08/03/2016
  3989                              <1> 	; 06/03/2016 (TRDOS 386 = TRDOS v2.0)
  3990                              <1> 	; 20/11/2010 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_rename')
  3991                              <1> 	; 16/11/2010 
  3992                              <1> 
  3993                              <1> get_rename_source_fchar:
  3994                              <1> 	; esi = file name
  3995 00009725 803E20              <1> 	cmp	byte [esi], 20h
  3996 00009728 7614                <1>         jna	short loc_rename_nofilename_retn
  3997                              <1> 
  3998 0000972A 8935[24690100]      <1> 	mov	[SourceFilePath], esi
  3999                              <1> 
  4000                              <1> rename_scan_source_file:
  4001 00009730 46                  <1> 	inc	esi
  4002 00009731 803E20              <1> 	cmp	byte [esi], 20h
  4003 00009734 7409                <1> 	je	short rename_scan_destination_file_1
  4004                              <1> 	;jb	short loc_rename_nofilename_retn
  4005 00009736 0F82D3EEFFFF        <1> 	jb	loc_cmd_failed
  4006 0000973C EBF2                <1> 	jmp	short rename_scan_source_file
  4007                              <1> 
  4008                              <1> loc_rename_nofilename_retn: ; 08/03/2016
  4009 0000973E C3                  <1> 	retn
  4010                              <1> 
  4011                              <1> rename_scan_destination_file_1:
  4012 0000973F C60600              <1> 	mov	byte [esi], 0
  4013                              <1> 
  4014                              <1> rename_scan_destination_file_2:
  4015 00009742 46                  <1> 	inc	esi  
  4016 00009743 803E20              <1> 	cmp	byte [esi], 20h
  4017 00009746 74FA                <1> 	je	short rename_scan_destination_file_2
  4018                              <1> 	;jb	short loc_rename_nofilename_retn
  4019 00009748 0F82C1EEFFFF        <1> 	jb	loc_cmd_failed
  4020                              <1> 
  4021 0000974E 8935[28690100]      <1> 	mov	[DestinationFilePath], esi
  4022                              <1> 
  4023                              <1> rename_scan_destination_file_3:
  4024 00009754 46                  <1> 	inc	esi  
  4025 00009755 803E20              <1> 	cmp	byte [esi], 20h
  4026 00009758 77FA                <1> 	ja	short rename_scan_destination_file_3
  4027                              <1> 
  4028 0000975A C60600              <1> 	mov	byte [esi], 0
  4029                              <1> 
  4030                              <1> loc_rename_save_current_drive:
  4031 0000975D 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  4032 00009763 8835[A2660100]      <1> 	mov	byte [RUN_CDRV], dh
  4033                              <1> 
  4034                              <1> loc_rename_sf_parse_path_name:
  4035 00009769 8B35[24690100]      <1> 	mov	esi, [SourceFilePath] 
  4036 0000976F BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  4037 00009774 E877150000          <1> 	call	parse_path_name
  4038 00009779 0F8290EEFFFF        <1> 	jc	loc_cmd_failed
  4039                              <1> 
  4040                              <1> loc_rename_sf_check_filename_exists:
  4041 0000977F BE[28680100]        <1> 	mov	esi, FindFile_Name
  4042 00009784 803E20              <1> 	cmp	byte [esi], 20h
  4043 00009787 0F8682EEFFFF        <1> 	jna	loc_cmd_failed
  4044                              <1> 
  4045                              <1> 	;mov	[DelFile_FNPointer], esi 
  4046                              <1> 
  4047                              <1> loc_rename_sf_drv:
  4048                              <1> 	;mov	dh, [Current_Drv]
  4049                              <1> 	;mov	[RUN_CDRV], dh
  4050                              <1> 
  4051 0000978D 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  4052 00009793 38F2                <1> 	cmp	dl, dh ; dh = [Current_Drv]
  4053 00009795 740B                <1> 	je	short rename_sf_change_directory
  4054                              <1> 
  4055 00009797 E8E0DFFFFF          <1> 	call	change_current_drive
  4056 0000979C 0F82ABF7FFFF        <1> 	jc	loc_file_rw_cmd_failed
  4057                              <1> 
  4058                              <1> rename_sf_change_directory:
  4059 000097A2 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  4060 000097A9 7618                <1> 	jna	short rename_sf_find
  4061                              <1> 
  4062 000097AB FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  4063 000097B1 BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  4064 000097B6 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  4065 000097B8 E81D0F0000          <1> 	call	change_current_directory
  4066 000097BD 0F828AF7FFFF        <1>  	jc	loc_file_rw_cmd_failed
  4067                              <1> 
  4068                              <1> ;rename_sf_change_prompt_dir_string:
  4069                              <1> 	;call	change_prompt_dir_string
  4070                              <1> 
  4071                              <1> rename_sf_find:
  4072                              <1> 	;mov	esi, [DelFile_FNPointer]
  4073 000097C3 BE[28680100]        <1> 	mov	esi, FindFile_Name
  4074                              <1> 
  4075 000097C8 66B80008            <1> 	mov	ax, 0800h ; Except volume labels
  4076 000097CC E84EF3FFFF          <1> 	call	find_first_file
  4077 000097D1 0F8276F7FFFF        <1> 	jc	loc_file_rw_cmd_failed
  4078                              <1> 
  4079                              <1> loc_rename_sf_ambgfn_check:
  4080 000097D7 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  4081                              <1> 	;	(Note: It was BX in TRDOS v1)
  4082                              <1> 	;jz	short loc_rename_sf_found
  4083 000097DA 0F8571FCFFFF        <1> 	jnz	loc_file_not_found
  4084                              <1> 
  4085                              <1> 	;mov	eax, 2 ; File not found sign
  4086                              <1> 	;stc
  4087                              <1> 	;jmp	loc_file_rw_cmd_failed   
  4088                              <1> 
  4089                              <1> loc_rename_sf_found:
  4090                              <1> 	; EDI = Directory buffer entry offset/address
  4091                              <1> 	; BL = File (or Directory) Attributes 
  4092                              <1> 	;	(Note: It was 'CL' in TRDOS v1)
  4093                              <1> 	; mov	bl, [EDI+0Bh]
  4094                              <1> 
  4095 000097E0 F6C307              <1> 	test	bl, 07h ; Attributes, S-H-R
  4096 000097E3 0F856EF7FFFF        <1> 	jnz	loc_permission_denied
  4097                              <1> 	
  4098 000097E9 BE[E6670100]        <1>         mov     esi, FindFile_Drv
  4099 000097EE BF[2C690100]        <1>         mov     edi, SourceFile_Drv
  4100 000097F3 B920000000          <1> 	mov	ecx, 32
  4101 000097F8 F3A5                <1> 	rep	movsd
  4102                              <1> 
  4103                              <1> loc_rename_df_parse_path_name:
  4104 000097FA 8B35[28690100]      <1> 	mov	esi, [DestinationFilePath]
  4105 00009800 BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  4106 00009805 E8E6140000          <1> 	call	parse_path_name
  4107 0000980A 7219                <1> 	jc	short loc_rename_df_cmd_failed
  4108                              <1> 
  4109                              <1> 	;mov	dh, [RUN_CDRV]
  4110 0000980C 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  4111                              <1> 
  4112                              <1> 	; 'rename' command is valid only for same dos drive and same dir!
  4113                              <1> 	; ('move' command must be used if source file and destination file
  4114                              <1> 	; directories are not same!) 
  4115 00009812 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  4116 00009818 38F2                <1> 	cmp	dl, dh ; are source and destination drives different ?!
  4117 0000981A 7509                <1> 	jne	short loc_rename_df_cmd_failed ; yes! 
  4118                              <1> 
  4119                              <1> rename_df_check_dirname_exists:
  4120 0000981C 803D[E7670100]00    <1> 	cmp	byte [FindFile_Directory], 0
  4121 00009823 760B                <1> 	jna	short rename_df_check_filename_exists
  4122                              <1> 
  4123                              <1> 	; different source file and destination file directories !
  4124                              <1> loc_rename_df_cmd_failed:
  4125 00009825 B801000000          <1> 	mov	eax, 1 ; TRDOS 'Bad command or file name' error
  4126 0000982A F9                  <1> 	stc
  4127 0000982B E91DF7FFFF          <1> 	jmp	loc_file_rw_cmd_failed
  4128                              <1> 	  
  4129                              <1> rename_df_check_filename_exists:
  4130 00009830 BE[28680100]        <1> 	mov	esi, FindFile_Name
  4131 00009835 E8A3F6FFFF          <1> 	call	check_filename
  4132 0000983A 0F82BFF7FFFF        <1> 	jc	loc_mkdir_invalid_dir_name_chars
  4133                              <1> 
  4134                              <1> 	;mov	[DelFile_FNPointer], esi 
  4135                              <1> 	;cmp	byte [esi], 20h
  4136                              <1> 	;ja	short loc_rename_df_find
  4137                              <1> 
  4138                              <1> 	;mov	dh, [Current_Drv] ; dh has not been changed
  4139                              <1> 
  4140                              <1> rename_df_drv_check_writable:
  4141 00009840 0FB6F6              <1> 	movzx	esi, dh
  4142                              <1> 	;movzx	esi, byte [Current_Drv]
  4143 00009843 81C600010900        <1> 	add	esi, Logical_DOSDisks
  4144                              <1> 
  4145 00009849 88F2                <1> 	mov	dl, dh ; dl = [Current_Drv]
  4146 0000984B 8A7601              <1> 	mov	dh, [esi+LD_DiskType]
  4147                              <1> 
  4148 0000984E 80FE01              <1> 	cmp	dh, 1 ; 0 = Invalid
  4149 00009851 7310                <1> 	jnb	short rename_df_compare_sf_df_name
  4150                              <1> 
  4151                              <1> 	; 16/10/2016 (13h -> 30)
  4152 00009853 B81E000000          <1> 	mov	eax, 30 ; 'Disk write-protected' error
  4153 00009858 8B1D[28690100]      <1> 	mov	ebx, [DestinationFilePath] 
  4154 0000985E E9EAF6FFFF          <1> 	jmp	loc_file_rw_cmd_failed
  4155                              <1> 
  4156                              <1> rename_df_compare_sf_df_name:
  4157 00009863 BE[28680100]        <1> 	mov	esi, FindFile_Name
  4158 00009868 BF[6E690100]        <1> 	mov	edi, SourceFile_Name
  4159 0000986D B90C000000          <1> 	mov	ecx, 12
  4160                              <1> rename_df_compare_sf_df_name_next: 
  4161 00009872 AC                  <1> 	lodsb
  4162 00009873 AE                  <1> 	scasb
  4163 00009874 7506                <1> 	jne	short loc_rename_df_find
  4164 00009876 08C0                <1> 	or	al, al
  4165 00009878 74AB                <1> 	jz	short loc_rename_df_cmd_failed
  4166 0000987A E2F6                <1> 	loop	rename_df_compare_sf_df_name_next 
  4167                              <1> 
  4168                              <1> loc_rename_df_find:
  4169                              <1> 	;mov	esi, [DelFile_FNPointer]
  4170 0000987C BE[28680100]        <1> 	mov	esi, FindFile_Name
  4171                              <1> 
  4172 00009881 6631C0              <1> 	xor	ax, ax ; Any
  4173 00009884 E896F2FFFF          <1> 	call	find_first_file
  4174                              <1> 	;jnc	short loc_rename_df_found
  4175                              <1> 	; 29/12/2017
  4176 00009889 0F83C8F6FFFF        <1> 	jnc	loc_permission_denied
  4177                              <1> 
  4178                              <1> loc_rename_df_check_error_code:
  4179                              <1> 	;cmp	eax, 2
  4180 0000988F 3C02                <1> 	cmp	al, 2 ; Not found error
  4181 00009891 7406                <1> 	je	short rename_df_move_find_struct_to_dest
  4182 00009893 F9                  <1> 	stc
  4183 00009894 E9B4F6FFFF          <1> 	jmp	loc_file_rw_cmd_failed
  4184                              <1> 
  4185                              <1> ;loc_rename_df_found:
  4186                              <1> 	; 05/11/2016
  4187                              <1> 	; Permission denied error
  4188                              <1> 	;mov	eax, ERR_PERM_DENIED ; 29/12/2017
  4189                              <1> 	;stc
  4190                              <1> 	;jmp	loc_permission_denied  ; 06/11/2016
  4191                              <1> 
  4192                              <1> rename_df_move_find_struct_to_dest:
  4193 00009899 BE[E6670100]        <1>         mov     esi, FindFile_Drv
  4194 0000989E BF[AC690100]        <1>         mov     edi, DestinationFile_Drv
  4195 000098A3 B920000000          <1> 	mov	ecx, 32
  4196 000098A8 F3A5                <1> 	rep	movsd
  4197                              <1> 
  4198                              <1> loc_rename_df_process_q_sf:
  4199                              <1> 	;mov	ecx, 12
  4200 000098AA B10C                <1> 	mov	cl, 12
  4201 000098AC BE[6E690100]        <1>  	mov	esi, SourceFile_Name
  4202 000098B1 BF[17180100]        <1> 	mov	edi, Rename_OldName
  4203                              <1> rename_df_process_q_nml_1_sf:
  4204 000098B6 AC                  <1> 	lodsb
  4205 000098B7 3C20                <1>         cmp	al, 20h
  4206 000098B9 7603                <1>         jna	short rename_df_process_q_nml_2_sf
  4207 000098BB AA                  <1> 	stosb
  4208 000098BC E2F8                <1> 	loop	rename_df_process_q_nml_1_sf
  4209                              <1> 
  4210                              <1> rename_df_process_q_nml_2_sf:
  4211 000098BE C60700              <1> 	mov	byte [edi], 0
  4212                              <1> 
  4213                              <1> loc_rename_df_process_q_df:
  4214                              <1> 	;mov	ecx, 12
  4215 000098C1 B10C                <1> 	mov	cl, 12
  4216 000098C3 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  4217 000098C8 BF[28180100]        <1> 	mov	edi, Rename_NewName
  4218                              <1> rename_df_process_q_nml_1_df:
  4219 000098CD AC                  <1> 	lodsb
  4220 000098CE 3C20                <1> 	cmp	al, 20h
  4221 000098D0 7603                <1> 	jna	short loc_rename_df_process_q_nml_2_df
  4222 000098D2 AA                  <1> 	stosb
  4223 000098D3 E2F8                <1> 	loop	rename_df_process_q_nml_1_df
  4224                              <1> 
  4225                              <1> loc_rename_df_process_q_nml_2_df:
  4226 000098D5 C60700              <1> 	mov	byte [edi], 0
  4227                              <1> 
  4228                              <1> loc_rename_confirmation_question:
  4229 000098D8 BE[EF170100]        <1> 	mov	esi, Msg_DoYouWantRename
  4230 000098DD E823D3FFFF          <1> 	call	print_msg
  4231                              <1> 
  4232 000098E2 A0[89690100]        <1> 	mov	al, [SourceFile_DirEntry+11] ; Attributes
  4233 000098E7 2410                <1> 	and	al, 10h
  4234 000098E9 750C                <1> 	jnz	short rename_confirmation_question_dir
  4235                              <1> 
  4236                              <1> rename_confirmation_question_file:
  4237 000098EB BE[06180100]        <1> 	mov	esi, Rename_File
  4238 000098F0 E810D3FFFF          <1> 	call	print_msg 
  4239 000098F5 EB0A                <1> 	jmp	short rename_confirmation_question_as 
  4240                              <1> 
  4241                              <1> rename_confirmation_question_dir:
  4242 000098F7 BE[0C180100]        <1> 	mov	esi, Rename_Directory
  4243 000098FC E804D3FFFF          <1> 	call	print_msg
  4244                              <1> 
  4245                              <1> rename_confirmation_question_as:
  4246 00009901 BE[17180100]        <1> 	mov	esi, Rename_OldName
  4247 00009906 E8FAD2FFFF          <1> 	call	print_msg
  4248 0000990B BE[24180100]        <1> 	mov	esi, Msg_File_rename_as
  4249 00009910 E8F0D2FFFF          <1> 	call	print_msg
  4250 00009915 BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  4251 0000991A E8E6D2FFFF          <1> 	call	print_msg
  4252                              <1> 
  4253                              <1> loc_rename_ask_again:
  4254 0000991F 30E4                <1> 	xor	ah, ah
  4255 00009921 E83475FFFF          <1> 	call	int16h
  4256 00009926 3C1B                <1> 	cmp	al, 1Bh
  4257 00009928 740F                <1> 	je	short loc_do_not_rename_file
  4258 0000992A 24DF                <1> 	and	al, 0DFh
  4259 0000992C A2[55170100]        <1> 	mov	[Y_N_nextline], al
  4260 00009931 3C59                <1> 	cmp	al, 'Y'
  4261 00009933 7404                <1> 	je	short loc_yes_rename_file
  4262 00009935 3C4E                <1> 	cmp	al, 'N'
  4263 00009937 75E6                <1> 	jne	short loc_rename_ask_again
  4264                              <1> 
  4265                              <1> loc_do_not_rename_file:
  4266                              <1> loc_yes_rename_file:
  4267 00009939 E848F7FFFF          <1> 	call	y_n_answer ; 29/12/2017
  4268                              <1> 	;cmp	al, 'Y' ; 'yes'
  4269                              <1> 	;cmc
  4270                              <1>         ;jnc	loc_file_rw_restore_retn
  4271 0000993E 3C4E                <1> 	cmp	al, 'N' ; 'no'
  4272 00009940 0F8407F6FFFF        <1>         je	loc_file_rw_restore_retn  
  4273                              <1> 
  4274 00009946 BE[28180100]        <1> 	mov	esi, Rename_NewName
  4275 0000994B 668B0D[A6690100]    <1> 	mov	cx, [SourceFile_DirEntryNumber] 
  4276 00009952 66A1[92690100]      <1> 	mov	ax, [SourceFile_DirEntry+20] ; First Cluster, HW 
  4277 00009958 C1E010              <1> 	shl	eax, 16 ; 13/11/2017
  4278 0000995B 66A1[98690100]      <1> 	mov	ax, [SourceFile_DirEntry+26] ; First Cluster, LW 
  4279                              <1> 
  4280 00009961 0FB61D[7B690100]    <1>   	movzx	ebx, byte [SourceFile_LongNameEntryLength]  
  4281 00009968 E8CB1B0000          <1>    	call	rename_directory_entry
  4282 0000996D E9FBF6FFFF          <1> 	jmp	loc_rename_file_ok	
  4283                              <1> ;loc_rename_file_ok:
  4284                              <1> ;	jc	loc_run_cmd_failed
  4285                              <1> ;	mov	esi, Msg_OK
  4286                              <1> ;	call	proc_printmsg
  4287                              <1> ;	jmp	loc_file_rw_restore_retn
  4288                              <1> 
  4289                              <1> move_file:
  4290                              <1> 	; 11/03/2016
  4291                              <1> 	; 09/03/2016
  4292                              <1> 	; 08/03/2016 (TRDOS 386 = TRDOS v2.0)
  4293                              <1> 	; 21/05/2011 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_move')
  4294                              <1> 	; 23/04/2011
  4295                              <1> 
  4296                              <1> get_move_source_fchar:
  4297                              <1> 	; esi = file name
  4298 00009972 803E20              <1> 	cmp	byte [esi], 20h
  4299 00009975 7614                <1>         jna	short loc_move_nofilename_retn
  4300                              <1> 
  4301 00009977 8935[24690100]      <1> 	mov	[SourceFilePath], esi
  4302                              <1> 
  4303                              <1> move_scan_source_file:
  4304 0000997D 46                  <1> 	inc	esi
  4305 0000997E 803E20              <1> 	cmp	byte [esi], 20h
  4306 00009981 7409                <1>         je      short move_scan_destination_1
  4307                              <1> 	;jb	short loc_move_nofilename_retn
  4308 00009983 0F8286ECFFFF        <1> 	jb	loc_cmd_failed
  4309 00009989 EBF2                <1> 	jmp	short move_scan_source_file
  4310                              <1> 
  4311                              <1> loc_move_nofilename_retn:
  4312 0000998B C3                  <1> 	retn
  4313                              <1> 
  4314                              <1> move_scan_destination_1:
  4315 0000998C C60600              <1> 	mov	byte [esi], 0
  4316                              <1> 
  4317                              <1> move_scan_destination_2:
  4318 0000998F 46                  <1> 	inc	esi  
  4319 00009990 803E20              <1> 	cmp	byte [esi], 20h
  4320 00009993 74FA                <1> 	je	short move_scan_destination_2
  4321                              <1> 	;jb	short loc_move_nofilename_retn
  4322 00009995 0F8274ECFFFF        <1> 	jb	loc_cmd_failed
  4323                              <1> 
  4324 0000999B 8935[28690100]      <1> 	mov	[DestinationFilePath], esi
  4325                              <1> 
  4326                              <1> move_scan_destination_3:
  4327 000099A1 46                  <1> 	inc	esi  
  4328 000099A2 803E20              <1> 	cmp	byte [esi], 20h
  4329 000099A5 77FA                <1> 	ja	short move_scan_destination_3
  4330 000099A7 C60600              <1> 	mov	byte [esi], 0
  4331                              <1> 
  4332                              <1> loc_move_scan_destination_OK:
  4333 000099AA 8B35[24690100]      <1> 	mov	esi, [SourceFilePath]
  4334 000099B0 8B3D[28690100]      <1> 	mov	edi, [DestinationFilePath]
  4335                              <1> 
  4336 000099B6 B001                <1> 	mov	al, 1  ; move procedure Phase 1
  4337 000099B8 E8F71B0000          <1> 	call	move_source_file_to_destination_file
  4338 000099BD 7328                <1> 	jnc	short move_source_file_to_destination_question
  4339                              <1> 
  4340                              <1> loc_move_cmd_failed_1:
  4341 000099BF 08C0                <1> 	or	al, al
  4342 000099C1 0F8448ECFFFF        <1> 	jz	loc_cmd_failed 
  4343 000099C7 3C11                <1> 	cmp	al, 11h
  4344 000099C9 740D                <1> 	je	short loc_msg_not_same_device   
  4345                              <1> 	;cmp	al, 05h
  4346                              <1> 	;cmp	al, ERR_PERM_DENIED ; 29/12/2017
  4347                              <1> 	;jne	loc_run_cmd_failed
  4348                              <1> 	;jmp	loc_permission_denied
  4349 000099CB 3C0B                <1> 	cmp	al, ERR_PERM_DENIED
  4350 000099CD 0F8484F5FFFF        <1> 	je	loc_permission_denied
  4351 000099D3 E962ECFFFF          <1> 	jmp	loc_run_cmd_failed
  4352                              <1> 
  4353                              <1> 	;mov	esi, Msg_Permission_denied
  4354                              <1> 	;call	print_msg
  4355                              <1> 	;jmp	loc_file_rw_restore_retn
  4356                              <1> 
  4357                              <1> loc_msg_not_same_device:
  4358 000099D8 BE[35180100]        <1> 	mov	esi, msg_not_same_drv 
  4359 000099DD E823D2FFFF          <1> 	call	print_msg
  4360 000099E2 E966F5FFFF          <1> 	jmp	loc_file_rw_restore_retn
  4361                              <1> 
  4362                              <1> move_source_file_to_destination_question:
  4363 000099E7 A0[2C690100]        <1>         mov     al, [SourceFile_Drv]
  4364 000099EC 0441                <1> 	add	al, 'A'
  4365 000099EE A2[97180100]        <1> 	mov	[msg_source_file_drv], al
  4366 000099F3 A0[AC690100]        <1>         mov     al, [DestinationFile_Drv]
  4367 000099F8 0441                <1> 	add	al, 'A'
  4368 000099FA A2[B6180100]        <1> 	mov	[msg_destination_file_drv], al
  4369                              <1> 
  4370 000099FF 57                  <1> 	push	edi ; *
  4371                              <1> 
  4372 00009A00 BE[7B180100]        <1> 	mov	esi, msg_source_file
  4373 00009A05 E8FBD1FFFF          <1> 	call	print_msg
  4374 00009A0A BE[2D690100]        <1> 	mov	esi, SourceFile_Directory
  4375 00009A0F 803E20              <1> 	cmp	byte [esi], 20h
  4376 00009A12 7605                <1> 	jna	short msftdfq_sfn
  4377 00009A14 E8ECD1FFFF          <1> 	call	print_msg
  4378                              <1> msftdfq_sfn:
  4379 00009A19 BE[6E690100]        <1> 	mov	esi, SourceFile_Name
  4380 00009A1E E8E2D1FFFF          <1> 	call	print_msg
  4381 00009A23 BE[9A180100]        <1> 	mov	esi, msg_destination_file
  4382 00009A28 E8D8D1FFFF          <1> 	call	print_msg
  4383 00009A2D BE[AD690100]        <1> 	mov	esi, DestinationFile_Directory
  4384 00009A32 803E20              <1> 	cmp	byte [esi], 20h
  4385 00009A35 7605                <1> 	jna	short msftdfq_dfn
  4386 00009A37 E8C9D1FFFF          <1> 	call	print_msg
  4387                              <1> msftdfq_dfn:
  4388 00009A3C BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  4389 00009A41 E8BFD1FFFF          <1> 	call	print_msg
  4390 00009A46 BE[B9180100]        <1> 	mov	esi, msg_copy_nextline
  4391 00009A4B E8B5D1FFFF          <1> 	call	print_msg
  4392 00009A50 BE[B9180100]        <1> 	mov	esi, msg_copy_nextline
  4393 00009A55 E8ABD1FFFF          <1> 	call	print_msg
  4394                              <1> 
  4395                              <1> loc_move_ask_for_new_file_yes_no:
  4396 00009A5A BE[47180100]        <1> 	mov	esi, Msg_DoYouWantMoveFile
  4397 00009A5F E8A1D1FFFF          <1> 	call	print_msg
  4398 00009A64 BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  4399 00009A69 E897D1FFFF          <1> 	call	print_msg
  4400                              <1> loc_move_ask_for_new_file_again:
  4401 00009A6E 30E4                <1> 	xor	ah, ah
  4402 00009A70 E8E573FFFF          <1> 	call	int16h
  4403 00009A75 3C1B                <1> 	cmp	al, 1Bh
  4404                              <1> 	;je	short loc_do_not_move_file
  4405 00009A77 7441                <1> 	je	short loc_move_y_n_escape
  4406 00009A79 24DF                <1> 	and	al, 0DFh
  4407 00009A7B A2[55170100]        <1>         mov     [Y_N_nextline], al
  4408 00009A80 3C59                <1> 	cmp	al, 'Y'
  4409 00009A82 7404                <1> 	je	short loc_yes_move_file
  4410 00009A84 3C4E                <1> 	cmp	al, 'N'
  4411 00009A86 75E6                <1> 	jne	short loc_move_ask_for_new_file_again
  4412                              <1> 
  4413                              <1> loc_do_not_move_file:
  4414                              <1> loc_yes_move_file:
  4415 00009A88 E8F9F5FFFF          <1> 	call	y_n_answer ; 29/12/2017
  4416 00009A8D 5F                  <1> 	pop	edi ; *
  4417                              <1> 	;cmp	al, 'Y' ; 'yes'
  4418                              <1> 	;cmc
  4419                              <1>         ;jnc	loc_file_rw_restore_retn
  4420 00009A8E 3C4E                <1> 	cmp	al, 'N' ; 'no'
  4421 00009A90 0F84B7F4FFFF        <1>         je	loc_file_rw_restore_retn
  4422                              <1> 
  4423                              <1> loc_move_yes_move_file:
  4424 00009A96 B002                <1> 	mov	al, 2 ; move procedure Phase 2
  4425 00009A98 E8171B0000          <1> 	call	move_source_file_to_destination_file
  4426                              <1> 	;jc	short loc_move_cmd_failed_2
  4427 00009A9D 0F83D0F5FFFF        <1>         jnc     move_source_file_to_destination_OK
  4428                              <1> 
  4429                              <1> ;move_source_file_to_destination_OK:
  4430                              <1> ;	mov	esi, Msg_OK
  4431                              <1> ;	call	print_msg
  4432                              <1> ;	jmp	loc_file_rw_restore_retn
  4433                              <1> 
  4434                              <1> loc_move_cmd_failed_2:
  4435 00009AA3 3C27                <1> 	cmp	al, 27h
  4436 00009AA5 0F858FEBFFFF        <1> 	jne	loc_run_cmd_failed
  4437                              <1> 
  4438 00009AAB BE[60180100]        <1> 	mov	esi, msg_insufficient_disk_space
  4439 00009AB0 E850D1FFFF          <1> 	call	print_msg
  4440                              <1> 
  4441 00009AB5 E993F4FFFF          <1> 	jmp	loc_file_rw_restore_retn
  4442                              <1> 
  4443                              <1> loc_move_y_n_escape:
  4444 00009ABA B04E                <1> 	mov	al, 'N' ; 'no'
  4445 00009ABC EBCA                <1> 	jmp	short loc_do_not_move_file
  4446                              <1> 
  4447                              <1> copy_file:
  4448                              <1> 	; 15/10/2016
  4449                              <1> 	; 24/03/2016
  4450                              <1> 	; 21/03/2016
  4451                              <1> 	; 15/03/2016 (TRDOS 386 = TRDOS v2.0)
  4452                              <1> 	; 21/05/2011 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_copy')
  4453                              <1> 	; 01/08/2010
  4454                              <1> 
  4455                              <1> get_copy_source_fchar:
  4456                              <1> 	; esi = file name
  4457 00009ABE 803E20              <1> 	cmp	byte [esi], 20h
  4458 00009AC1 7614                <1>         jna     short loc_copy_nofilename_retn
  4459                              <1> 
  4460 00009AC3 8935[24690100]      <1> 	mov	[SourceFilePath], esi
  4461                              <1> 
  4462                              <1> copy_scan_source_file:
  4463 00009AC9 46                  <1> 	inc	esi  
  4464 00009ACA 803E20              <1> 	cmp	byte [esi], 20h
  4465 00009ACD 7409                <1> 	je	short copy_scan_destination_1
  4466                              <1> 	;jb	short loc_copy_nofilename_retn
  4467 00009ACF 0F823AEBFFFF        <1> 	jb	loc_cmd_failed
  4468 00009AD5 EBF2                <1> 	jmp	short copy_scan_source_file
  4469                              <1> 
  4470                              <1> loc_copy_nofilename_retn:
  4471 00009AD7 C3                  <1> 	retn
  4472                              <1> 
  4473                              <1> copy_scan_destination_1:
  4474 00009AD8 C60600              <1> 	mov	byte [esi], 0
  4475                              <1> 
  4476                              <1> copy_scan_destination_2:
  4477 00009ADB 46                  <1> 	inc	esi  
  4478 00009ADC 803E20              <1> 	cmp	byte [esi], 20h
  4479 00009ADF 74FA                <1> 	je	short copy_scan_destination_2
  4480                              <1> 	;jb	short loc_copy_nofilename_retn
  4481 00009AE1 0F8228EBFFFF        <1> 	jb	loc_cmd_failed
  4482                              <1> 
  4483 00009AE7 8935[28690100]      <1> 	mov	[DestinationFilePath], esi
  4484                              <1> 
  4485                              <1> copy_scan_destination_3:
  4486 00009AED 46                  <1> 	inc	esi  
  4487 00009AEE 803E20              <1> 	cmp	byte [esi], 20h
  4488 00009AF1 77FA                <1> 	ja	short copy_scan_destination_3
  4489 00009AF3 C60600              <1> 	mov	byte [esi], 0
  4490                              <1> 
  4491                              <1> loc_copy_save_current_drive:
  4492 00009AF6 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  4493 00009AFC 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  4494                              <1> 
  4495                              <1> copy_source_file_to_destination_phase_1:
  4496 00009B02 8B35[24690100]      <1> 	mov	esi, [SourceFilePath]
  4497 00009B08 8B3D[28690100]      <1> 	mov	edi, [DestinationFilePath]
  4498                              <1> 
  4499 00009B0E B001                <1> 	mov	al, 1  ; copy procedure Phase 1
  4500 00009B10 E83C1D0000          <1> 	call	copy_source_file_to_destination_file
  4501 00009B15 732B                <1> 	jnc	short copy_source_file_to_destination_question
  4502                              <1> 
  4503                              <1> loc_copy_cmd_failed_1:
  4504                              <1> 	; 18/03/2016 (restore current drive and directory)
  4505 00009B17 08C0                <1> 	or	al, al
  4506 00009B19 7507                <1> 	jnz	short loc_copy_cmd_failed_2
  4507                              <1> 
  4508 00009B1B FEC0                <1>         inc     al ; mov al, 1 ; Bad command or file name !
  4509 00009B1D E918EBFFFF          <1> 	jmp	loc_run_cmd_failed
  4510                              <1> 
  4511                              <1> loc_copy_cmd_failed_2:
  4512 00009B22 3C27                <1> 	cmp	al, 27h ; Insufficient disk space 
  4513 00009B24 740D                <1> 	je	short loc_file_write_insuff_disk_space_msg
  4514                              <1>  
  4515                              <1> 	; 29/12/2017
  4516                              <1> 	;cmp	al, 05h
  4517 00009B26 3C0B                <1> 	cmp	al, ERR_PERM_DENIED
  4518 00009B28 0F850CEBFFFF        <1> 	jne	loc_run_cmd_failed
  4519                              <1> 	
  4520 00009B2E E924F4FFFF          <1> 	jmp	loc_permission_denied
  4521                              <1> 
  4522                              <1> loc_file_write_insuff_disk_space_msg:
  4523 00009B33 BE[60180100]        <1> 	mov	esi, msg_insufficient_disk_space
  4524 00009B38 E8C8D0FFFF          <1> 	call	print_msg
  4525 00009B3D E90BF4FFFF          <1>         jmp     loc_file_rw_restore_retn 
  4526                              <1> 
  4527                              <1> copy_source_file_to_destination_question:
  4528 00009B42 57                  <1> 	push	edi ; *
  4529                              <1> 
  4530                              <1> 	; dh = source file attributes
  4531                              <1> 	; dl > 0 -> destination file found
  4532 00009B43 20D2                <1> 	and	dl, dl            
  4533 00009B45 7449                <1> 	jz	short copy_source_file_to_destination_pass_owrq
  4534                              <1> 
  4535                              <1> loc_copy_ask_for_owr_yes_no:
  4536 00009B47 BE[BC180100]        <1> 	mov	esi, Msg_DoYouWantOverWriteFile
  4537 00009B4C E8B4D0FFFF          <1> 	call	print_msg
  4538 00009B51 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  4539 00009B56 E8AAD0FFFF          <1> 	call	print_msg
  4540 00009B5B BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  4541 00009B60 E8A0D0FFFF          <1> 	call	print_msg
  4542                              <1> 
  4543                              <1> loc_copy_ask_for_owr_again:
  4544 00009B65 30E4                <1> 	xor	ah, ah
  4545 00009B67 E8EE72FFFF          <1> 	call	int16h
  4546 00009B6C 3C1B                <1> 	cmp	al, 1Bh
  4547                              <1>         ;je     loc_do_not_copy_file
  4548 00009B6E 7419                <1>         je      short loc_copy_y_n_escape
  4549 00009B70 24DF                <1> 	and	al, 0DFh
  4550 00009B72 A2[55170100]        <1>         mov     [Y_N_nextline], al
  4551 00009B77 3C59                <1> 	cmp	al, 'Y'
  4552 00009B79 0F84B1000000        <1>         je      loc_yes_copy_file
  4553 00009B7F 3C4E                <1> 	cmp	al, 'N'
  4554 00009B81 0F84A9000000        <1>         je      loc_do_not_copy_file
  4555 00009B87 EBDC                <1> 	jmp	short loc_copy_ask_for_owr_again
  4556                              <1> 
  4557                              <1> loc_copy_y_n_escape:
  4558 00009B89 B04E                <1> 	mov	al, 'N' ; 'no'
  4559 00009B8B E9A0000000          <1>         jmp     loc_do_not_copy_file
  4560                              <1> 
  4561                              <1> copy_source_file_to_destination_pass_owrq:
  4562 00009B90 A0[2C690100]        <1> 	mov     al, [SourceFile_Drv]
  4563 00009B95 0441                <1> 	add	al, 'A'
  4564 00009B97 A2[97180100]        <1> 	mov	[msg_source_file_drv], al
  4565 00009B9C A0[AC690100]        <1>         mov     al, [DestinationFile_Drv]
  4566 00009BA1 0441                <1> 	add	al, 'A'
  4567 00009BA3 A2[B6180100]        <1> 	mov	[msg_destination_file_drv], al
  4568                              <1> 
  4569 00009BA8 BE[7B180100]        <1> 	mov	esi, msg_source_file
  4570 00009BAD E853D0FFFF          <1> 	call	print_msg
  4571 00009BB2 BE[2D690100]        <1> 	mov	esi, SourceFile_Directory
  4572 00009BB7 803E20              <1> 	cmp	byte [esi], 20h
  4573 00009BBA 7605                <1> 	jna	short csftdfq_sfn
  4574 00009BBC E844D0FFFF          <1> 	call	print_msg
  4575                              <1> csftdfq_sfn:
  4576 00009BC1 BE[6E690100]        <1> 	mov	esi, SourceFile_Name
  4577 00009BC6 E83AD0FFFF          <1> 	call	print_msg
  4578 00009BCB BE[9A180100]        <1> 	mov	esi, msg_destination_file
  4579 00009BD0 E830D0FFFF          <1> 	call	print_msg
  4580 00009BD5 BE[AD690100]        <1> 	mov	esi, DestinationFile_Directory
  4581 00009BDA 803E20              <1> 	cmp	byte [esi], 20h
  4582 00009BDD 7605                <1> 	jna	short csftdfq_dfn
  4583 00009BDF E821D0FFFF          <1> 	call	print_msg
  4584                              <1> csftdfq_dfn:
  4585 00009BE4 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  4586 00009BE9 E817D0FFFF          <1> 	call	print_msg
  4587 00009BEE BE[B9180100]        <1> 	mov	esi, msg_copy_nextline
  4588 00009BF3 E80DD0FFFF          <1> 	call	print_msg
  4589 00009BF8 BE[B9180100]        <1> 	mov	esi, msg_copy_nextline
  4590 00009BFD E803D0FFFF          <1> 	call	print_msg
  4591                              <1> 
  4592                              <1> loc_copy_ask_for_new_file_yes_no:
  4593 00009C02 BE[DB180100]        <1> 	mov	esi, Msg_DoYouWantCopyFile
  4594 00009C07 E8F9CFFFFF          <1> 	call	print_msg
  4595 00009C0C BE[4B170100]        <1> 	mov	esi, Msg_YesNo
  4596 00009C11 E8EFCFFFFF          <1> 	call	print_msg
  4597                              <1> 
  4598                              <1> loc_copy_ask_for_new_file_again:
  4599 00009C16 30E4                <1> 	xor	ah, ah
  4600 00009C18 E83D72FFFF          <1> 	call	int16h
  4601 00009C1D 3C1B                <1> 	cmp	al, 1Bh
  4602 00009C1F 740F                <1> 	je	short loc_do_not_copy_file
  4603 00009C21 24DF                <1> 	and	al, 0DFh
  4604 00009C23 A2[55170100]        <1>         mov     [Y_N_nextline], al
  4605 00009C28 3C59                <1> 	cmp	al, 'Y'
  4606 00009C2A 7404                <1> 	je	short loc_yes_copy_file
  4607 00009C2C 3C4E                <1> 	cmp	al, 'N'
  4608 00009C2E 75E6                <1> 	jne	short loc_copy_ask_for_new_file_again
  4609                              <1> 
  4610                              <1> loc_do_not_copy_file:
  4611                              <1> loc_yes_copy_file:
  4612 00009C30 E851F4FFFF          <1> 	call	y_n_answer ; 29/12/2017
  4613 00009C35 5F                  <1> 	pop	edi ; *
  4614                              <1> 	;cmp	al, 'Y' ; 'yes'
  4615                              <1> 	;cmc
  4616                              <1>         ;jnc	loc_file_rw_restore_retn
  4617 00009C36 3C4E                <1> 	cmp	al, 'N' ; 'no'
  4618 00009C38 0F840FF3FFFF        <1>         je	loc_file_rw_restore_retn
  4619                              <1> 
  4620                              <1> copy_source_file_to_destination_pass_q:
  4621 00009C3E B002                <1> 	mov	al, 2  ; copy procedure Phase 2
  4622 00009C40 E80C1C0000          <1> 	call	copy_source_file_to_destination_file
  4623                              <1> 	;jc	short loc_file_write_check_disk_space_err
  4624                              <1> 
  4625                              <1> 	; 24/03/2016
  4626                              <1> 	;push	cx
  4627 00009C45 51                  <1> 	push	ecx ; 29/12/2017
  4628 00009C46 BE[B9180100]        <1> 	mov	esi, msg_copy_nextline
  4629 00009C4B E8B5CFFFFF          <1> 	call	print_msg
  4630 00009C50 58                  <1> 	pop	eax ; 29/12/2017
  4631                              <1> 	;;pop	cx
  4632                              <1> 	;pop	ax
  4633                              <1> 
  4634                              <1> 	;or	cl, cl
  4635 00009C51 08C0                <1> 	or	al, al
  4636 00009C53 7419                <1> 	jz	short copy_source_file_to_destination_OK
  4637                              <1> 	
  4638                              <1> 	; 15/10/2016 (1Dh -> 18)
  4639                              <1> 	; 18/03/2016 (1Dh)
  4640                              <1> 	;cmp	cl, 18 ; write error
  4641 00009C55 3C12                <1> 	cmp	al, 18
  4642 00009C57 7506                <1> 	jne	short copy_source_file_to_destination_not_OK
  4643                              <1> 	;
  4644                              <1> 	;mov	al, cl ; error number (write fault!)
  4645 00009C59 F9                  <1> 	stc
  4646 00009C5A E9EEF2FFFF          <1> 	jmp	loc_file_rw_cmd_failed
  4647                              <1> 
  4648                              <1> copy_source_file_to_destination_not_OK:
  4649 00009C5F BE[F4180100]        <1> 	mov	esi, Msg_read_file_error_before_EOF
  4650 00009C64 E89CCFFFFF          <1> 	call	print_msg
  4651 00009C69 E9DFF2FFFF          <1> 	jmp	loc_file_rw_restore_retn	      
  4652                              <1>  
  4653                              <1> copy_source_file_to_destination_OK:
  4654 00009C6E BE[59170100]        <1> 	mov	esi, Msg_OK
  4655 00009C73 E88DCFFFFF          <1> 	call	print_msg
  4656                              <1> 
  4657 00009C78 E9D0F2FFFF          <1> 	jmp	loc_file_rw_restore_retn
  4658                              <1> 
  4659                              <1> ;loc_file_write_check_disk_space_err:
  4660                              <1> 	;cmp	al, 27h ; Insufficient disk space 
  4661                              <1> 	;je	loc_file_write_insuff_disk_space_msg
  4662                              <1>         ;jb	loc_file_rw_cmd_failed
  4663                              <1> 
  4664                              <1> 	;call	print_misc_error_msg ; 15/03/2016
  4665                              <1>         ;jmp	loc_file_rw_restore_retn 
  4666                              <1> 
  4667                              <1> change_fs_file_attributes:
  4668                              <1> 	; 04/03/2016 ; Temporary
  4669                              <1> 	; AL = File or directory attributes
  4670                              <1> 	; AH = 0 -> Attributes are in MS-DOS format
  4671                              <1> 	; AH > 0 -> Attributes are in SINGLIX format
  4672                              <1> 	;push	ebx
  4673                              <1> 	; ... do somethings here ...
  4674                              <1> 	;pop	ebx
  4675                              <1> 	; BL = File or directory attributes
  4676 00009C7D C3                  <1> 	retn
  4677                              <1> 
  4678                              <1> set_get_env:
  4679                              <1> 	; 11/04/2016 (TRDOS 386 = TRDOS v2.0)
  4680                              <1> 	; 02/09/2011 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_set')
  4681                              <1> 	; 2005 - 28/08/2011 
  4682                              <1> get_setenv_fchar:
  4683                              <1> 	; esi = environment variable/string
  4684 00009C7E 8A06                <1> 	mov	al, [esi]
  4685 00009C80 3C20                <1> 	cmp	al, 20h
  4686 00009C82 771E                <1> 	ja	short loc_find_env
  4687                              <1> 
  4688 00009C84 BE00300900          <1> 	mov	esi, Env_Page
  4689                              <1> loc_print_setline:
  4690 00009C89 803E00              <1> 	cmp	byte [esi], 0
  4691 00009C8C 7613                <1> 	jna	short loc_setenv_retn
  4692 00009C8E E872CFFFFF          <1> 	call	print_msg
  4693 00009C93 56                  <1> 	push	esi
  4694 00009C94 BE[631F0100]        <1> 	mov	esi, nextline
  4695 00009C99 E867CFFFFF          <1> 	call	print_msg 
  4696 00009C9E 5E                  <1> 	pop	esi
  4697 00009C9F EBE8                <1> 	jmp	short loc_print_setline   
  4698                              <1> 
  4699                              <1> loc_setenv_retn: 
  4700 00009CA1 C3                  <1> 	retn
  4701                              <1> 
  4702                              <1> loc_find_env:
  4703 00009CA2 3C3D                <1> 	cmp	al, '='
  4704 00009CA4 0F8465E9FFFF        <1> 	je	loc_cmd_failed
  4705                              <1> 
  4706 00009CAA 56                  <1> 	push	esi
  4707                              <1> loc_repeat_env_equal_check:
  4708 00009CAB 46                  <1> 	inc	esi
  4709 00009CAC 803E3D              <1> 	cmp	byte [esi], '='
  4710 00009CAF 7431                <1> 	je	short pass_env_equal_check
  4711 00009CB1 803E20              <1> 	cmp	byte [esi], 20h
  4712 00009CB4 73F5                <1> 	jnb	short loc_repeat_env_equal_check
  4713 00009CB6 C60600              <1> 	mov	byte [esi], 0 
  4714 00009CB9 5E                  <1> 	pop	esi
  4715 00009CBA BF[46600100]        <1> 	mov	edi, TextBuffer ; out buffer
  4716 00009CBF B9FF000000          <1> 	mov	ecx, 255 ; maximum size (limit)
  4717 00009CC4 30C0                <1> 	xor	al, al ; 0 -> use [ESI]
  4718 00009CC6 E89E000000          <1> 	call	get_environment_string
  4719 00009CCB 72D4                <1> 	jc	short loc_setenv_retn
  4720                              <1> 
  4721 00009CCD BE[46600100]        <1> 	mov	esi, TextBuffer
  4722 00009CD2 E82ECFFFFF          <1> 	call	print_msg
  4723 00009CD7 BE[631F0100]        <1> 	mov	esi, nextline
  4724 00009CDC E824CFFFFF          <1> 	call	print_msg
  4725                              <1> 
  4726 00009CE1 C3                  <1> 	retn 
  4727                              <1>               
  4728                              <1> pass_env_equal_check:
  4729 00009CE2 46                  <1> 	inc	esi
  4730 00009CE3 803E20              <1> 	cmp	byte [esi], 20h
  4731 00009CE6 73FA                <1> 	jnb	short pass_env_equal_check
  4732 00009CE8 C60600              <1> 	mov	byte [esi], 0	
  4733                              <1> 
  4734                              <1> loc_call_set_env_string:
  4735 00009CEB 5E                  <1> 	pop	esi
  4736 00009CEC E83B010000          <1> 	call	set_environment_string
  4737 00009CF1 73AE                <1> 	jnc	short loc_setenv_retn
  4738                              <1> 
  4739                              <1> loc_set_cmd_failed:
  4740 00009CF3 3C08                <1> 	cmp	al, 08h
  4741 00009CF5 0F8514E9FFFF        <1> 	jne	loc_cmd_failed
  4742                              <1> 
  4743 00009CFB BE[34190100]        <1> 	mov	esi, Msg_No_Set_Space
  4744 00009D00 E800CFFFFF          <1> 	call	print_msg
  4745                              <1> 
  4746 00009D05 C3                  <1> 	retn
  4747                              <1> 
  4748                              <1> set_get_path:
  4749                              <1> 	; 11/04/2016 (TRDOS 386 = TRDOS v2.0)
  4750                              <1> 	; 03/09/2011 (TRDOS v1, CMD_INTR.ASM, 'cmp_cmd_path')
  4751                              <1> 	; 2005
  4752                              <1> get_path_fchar:
  4753                              <1>  	; esi = path
  4754 00009D06 803E20              <1> 	cmp	byte [esi], 20h
  4755 00009D09 7737                <1> 	ja	short loc_set_path
  4756                              <1> 
  4757 00009D0B BE00300900          <1> 	mov	esi, Env_Page
  4758                              <1> loc_print_path:
  4759 00009D10 803E00              <1> 	cmp	byte [esi], 0
  4760 00009D13 762C                <1> 	jna	short loc_path_retn
  4761                              <1> 
  4762 00009D15 BE[93130100]        <1> 	mov	esi, Cmd_Path ; 'PATH' address
  4763 00009D1A BF[46600100]        <1> 	mov	edi, TextBuffer ; out buffer
  4764 00009D1F 30C0                <1> 	xor	al, al  ; use [ESI]
  4765 00009D21 B9FF000000          <1> 	mov	ecx, 255 ; maximum size (limit)
  4766 00009D26 E83E000000          <1> 	call	get_environment_string
  4767 00009D2B 7214                <1> 	jc	short loc_path_retn
  4768                              <1> 
  4769 00009D2D BE[46600100]        <1> 	mov	esi, TextBuffer
  4770 00009D32 E8CECEFFFF          <1> 	call	print_msg
  4771 00009D37 BE[631F0100]        <1> 	mov	esi, nextline
  4772 00009D3C E8C4CEFFFF          <1> 	call	print_msg   
  4773                              <1> 
  4774                              <1> loc_path_retn: 
  4775 00009D41 C3                  <1> 	retn
  4776                              <1> 
  4777                              <1> loc_set_path:
  4778 00009D42 56                  <1> 	push	esi 
  4779                              <1> loc_set_path_find_end:
  4780 00009D43 46                  <1> 	inc	esi
  4781 00009D44 803E20              <1> 	cmp	byte [esi], 20h
  4782 00009D47 73FA                <1> 	jnb	short loc_set_path_find_end
  4783 00009D49 C60600              <1> 	mov	byte [esi], 0 
  4784                              <1> loc_set_path_header: 
  4785 00009D4C 5E                  <1> 	pop	esi
  4786                              <1> set_path_x: ; 31/12/2017 ('syspath')	  
  4787 00009D4D 4E                  <1> 	dec	esi
  4788 00009D4E C6063D              <1> 	mov	byte [esi], '='
  4789 00009D51 4E                  <1> 	dec	esi
  4790 00009D52 C60648              <1> 	mov	byte [esi], 'H'
  4791 00009D55 4E                  <1> 	dec	esi
  4792 00009D56 C60654              <1> 	mov	byte [esi], 'T'
  4793 00009D59 4E                  <1> 	dec	esi
  4794 00009D5A C60641              <1> 	mov	byte [esi], 'A'
  4795 00009D5D 4E                  <1> 	dec	esi
  4796 00009D5E C60650              <1> 	mov	byte [esi], 'P'   
  4797                              <1> 
  4798                              <1> loc_path_call_set_env_string:
  4799 00009D61 E8C6000000          <1> 	call	set_environment_string
  4800 00009D66 728B                <1>         jc	short loc_set_cmd_failed
  4801                              <1> 
  4802 00009D68 C3                  <1> 	retn              
  4803                              <1> 
  4804                              <1> get_environment_string:
  4805                              <1> 	; 12/04/2016
  4806                              <1> 	; 11/04/2016
  4807                              <1> 	; 05/04/2016 (TRDOS 386 = TRDOS v2.0)
  4808                              <1> 	; 02/09/2011 (TRDOS v1, MAINPROG.ASM)
  4809                              <1> 	; 28/08/2011
  4810                              <1> 	; INPUT->
  4811                              <1> 	;	EDI = Output buffer
  4812                              <1> 	;	CX = Buffer length (<= ENV_PAGE_SIZE)
  4813                              <1> 	;
  4814                              <1> 	;	AL > 0 = AL = String sequence number
  4815                              <1> 	;	AL = 0 -> ESI = ASCIIZ Set word 
  4816                              <1> 	;		(environment variable)
  4817                              <1> 	; OUTPUT ->
  4818                              <1> 	;	ESI is not changed
  4819                              <1> 	;	EDI is not changed
  4820                              <1> 	;	EAX = String length (with zero tail)
  4821                              <1> 	;	EDX = Environment variables page address
  4822                              <1> 	;	CF = 1 -> Not found (EAX not valid)
  4823                              <1> 	;
  4824                              <1> 	; (Modified registers: EAX, EDX) 
  4825                              <1> 
  4826 00009D69 BA00300900          <1> 	mov	edx, Env_Page
  4827 00009D6E 803A00              <1> 	cmp	byte [edx], 0
  4828 00009D71 7474                <1> 	jz	short get_env_string_with_word_stc_retn
  4829                              <1> 
  4830 00009D73 66890D[B06A0100]    <1> 	mov	[env_var_length], cx
  4831                              <1> 
  4832 00009D7A 51                  <1> 	push	ecx ; *
  4833 00009D7B 56                  <1> 	push	esi ; **
  4834                              <1> 
  4835 00009D7C 08C0                <1> 	or	al, al
  4836 00009D7E 7449                <1> 	jz	short get_env_string_with_word
  4837                              <1> 
  4838                              <1> get_env_string_with_seq_number:
  4839 00009D80 B101                <1> 	mov	cl, 1
  4840 00009D82 88C5                <1> 	mov	ch, al
  4841 00009D84 31C0                <1> 	xor	eax, eax
  4842 00009D86 89D6                <1> 	mov	esi, edx ; Env_Page
  4843                              <1> 
  4844                              <1> get_env_string_seq_number_check:
  4845 00009D88 38CD                <1> 	cmp	ch, cl
  4846 00009D8A 7726                <1> 	ja	short get_env_string_seq_number_next
  4847                              <1> 
  4848                              <1> get_env_string_move_to_buff:
  4849 00009D8C 57                  <1> 	push	edi ; ***
  4850                              <1> 
  4851 00009D8D 29D2                <1> 	sub	edx, edx
  4852                              <1> 
  4853                              <1> get_env_string_seq_number_repeat1:
  4854 00009D8F 42                  <1> 	inc	edx
  4855 00009D90 AC                  <1> 	lodsb
  4856 00009D91 AA                  <1> 	stosb
  4857                              <1> 
  4858 00009D92 66FF0D[B06A0100]    <1> 	dec	word [env_var_length]
  4859 00009D99 7508                <1> 	jnz	short get_env_string_seq_number_repeat3
  4860                              <1> 
  4861                              <1> get_env_string_seq_number_repeat2:
  4862 00009D9B 20C0                <1> 	and	al, al
  4863 00009D9D 7408                <1> 	jz	short get_env_string_seq_number_ok
  4864 00009D9F 42                  <1> 	inc	edx
  4865 00009DA0 AC                  <1> 	lodsb
  4866 00009DA1 EBF8                <1> 	jmp	short get_env_string_seq_number_repeat2
  4867                              <1> 
  4868                              <1> get_env_string_seq_number_repeat3:
  4869 00009DA3 08C0                <1> 	or	al, al
  4870 00009DA5 75E8                <1> 	jnz	short get_env_string_seq_number_repeat1
  4871                              <1> 
  4872                              <1> get_env_string_seq_number_ok:
  4873 00009DA7 5F                  <1> 	pop	edi ; ***
  4874 00009DA8 89D0                <1> 	mov	eax, edx ; Length of the environment string
  4875                              <1> 			 ; (ASCIIZ, includes ZERO tail)
  4876 00009DAA BA00300900          <1> 	mov	edx, Env_Page
  4877                              <1> 
  4878                              <1> get_env_string_stc_retn:
  4879 00009DAF 5E                  <1> 	pop	esi ; **
  4880 00009DB0 59                  <1> 	pop	ecx ; *
  4881 00009DB1 C3                  <1> 	retn   
  4882                              <1> 	
  4883                              <1> get_env_string_seq_number_next:
  4884 00009DB2 AC                  <1> 	lodsb
  4885 00009DB3 08C0                <1> 	or	al, al
  4886 00009DB5 75FB                <1> 	jnz	short get_env_string_seq_number_next
  4887                              <1> 
  4888 00009DB7 81FE00320900        <1> 	cmp	esi, Env_Page + Env_Page_Size ; +512 (+4096)
  4889 00009DBD F5                  <1> 	cmc
  4890 00009DBE 72EF                <1> 	jc	short get_env_string_stc_retn
  4891                              <1> 
  4892 00009DC0 AC                  <1> 	lodsb
  4893 00009DC1 3C01                <1> 	cmp	al, 1
  4894 00009DC3 72EA                <1> 	jb	short get_env_string_stc_retn
  4895 00009DC5 FEC1                <1> 	inc	cl
  4896 00009DC7 EBBF                <1> 	jmp	short get_env_string_seq_number_check
  4897                              <1> 
  4898                              <1> get_env_string_with_word:
  4899 00009DC9 31C9                <1> 	xor	ecx, ecx
  4900                              <1> 
  4901                              <1> get_env_string_calc_word_length:
  4902 00009DCB AC                  <1> 	lodsb 
  4903 00009DCC 3C20                <1> 	cmp	al, 20h
  4904 00009DCE 7211                <1> 	jb	short get_env_string_calc_word_length_ok
  4905                              <1> 	;inc	cx
  4906 00009DD0 FEC1                <1> 	inc	cl
  4907                              <1> 
  4908 00009DD2 3C61                <1> 	cmp	al, 'a'
  4909 00009DD4 72F5                <1> 	jb	short get_env_string_calc_word_length
  4910 00009DD6 3C7A                <1> 	cmp	al, 'z'
  4911 00009DD8 77F1                <1> 	ja	short get_env_string_calc_word_length
  4912 00009DDA 24DF                <1> 	and	al, 0DFh
  4913 00009DDC 8846FF              <1> 	mov	[esi-1], al
  4914 00009DDF EBEA                <1> 	jmp	short get_env_string_calc_word_length
  4915                              <1> 	
  4916                              <1> get_env_string_calc_word_length_ok:
  4917 00009DE1 08C9                <1> 	or	cl, cl
  4918 00009DE3 7506                <1> 	jnz	short get_env_string_calc_word_length_save
  4919                              <1>      
  4920 00009DE5 5E                  <1> 	pop	esi ; **
  4921                              <1> 
  4922                              <1> get_env_string_stc_retn1:
  4923 00009DE6 59                  <1> 	pop	ecx ; *
  4924                              <1>         
  4925                              <1> get_env_string_with_word_stc_retn:
  4926 00009DE7 31C0                <1> 	xor	eax, eax  
  4927 00009DE9 F9                  <1> 	stc
  4928 00009DEA C3                  <1> 	retn
  4929                              <1>   
  4930                              <1> get_env_string_calc_word_length_save:
  4931 00009DEB 871C24              <1> 	xchg	ebx, [esp] ; **
  4932 00009DEE 89DE                <1> 	mov	esi, ebx 
  4933                              <1> 		; Start of the env string (to be searched)
  4934                              <1> 
  4935 00009DF0 57                  <1> 	push	edi ; ***
  4936 00009DF1 89D7                <1> 	mov	edi, edx ; Env_Page
  4937                              <1> 
  4938                              <1> get_env_string_compare:
  4939 00009DF3 57                  <1> 	push	edi ; ****
  4940 00009DF4 51                  <1> 	push	ecx ; ***** ; Variable name length
  4941                              <1> 
  4942                              <1> get_env_string_compare_rep:
  4943 00009DF5 AC                  <1> 	lodsb
  4944 00009DF6 AE                  <1> 	scasb
  4945 00009DF7 7511                <1> 	jne	short get_env_string_compare_next1
  4946 00009DF9 E2FA                <1> 	loop	get_env_string_compare_rep
  4947                              <1> 	
  4948 00009DFB 803F3D              <1> 	cmp	byte [edi], '='
  4949 00009DFE 750A                <1> 	jne	short get_env_string_compare_next1
  4950                              <1>  
  4951 00009E00 59                  <1> 	pop	ecx ; *****
  4952 00009E01 5F                  <1> 	pop	edi ; ****
  4953 00009E02 89FE                <1> 	mov	esi, edi
  4954 00009E04 5F                  <1> 	pop	edi ; ***
  4955 00009E05 871C24              <1> 	xchg	ebx, [esp] ; **
  4956 00009E08 EB82                <1> 	jmp	short get_env_string_move_to_buff
  4957                              <1> 
  4958                              <1> get_env_string_compare_next1:
  4959 00009E0A 89FE                <1> 	mov	esi, edi
  4960 00009E0C 59                  <1> 	pop	ecx ; *****
  4961 00009E0D 5F                  <1> 	pop	edi ; ****
  4962                              <1> get_env_string_compare_next2:
  4963 00009E0E 81FEFF310900        <1> 	cmp	esi, Env_Page + Env_Page_Size - 1 ; +511 (+4095)
  4964 00009E14 7310                <1> 	jnb	short get_env_string_compare_not_ok
  4965 00009E16 20C0                <1> 	and	al, al
  4966 00009E18 AC                  <1> 	lodsb
  4967 00009E19 75F3                <1> 	jnz	short get_env_string_compare_next2
  4968 00009E1B 08C0                <1> 	or	al, al
  4969 00009E1D 7407                <1> 	jz	short get_env_string_compare_not_ok
  4970 00009E1F 4E                  <1> 	dec	esi ; 12/04/2016
  4971 00009E20 89F7                <1> 	mov	edi, esi
  4972 00009E22 89DE                <1> 	mov	esi, ebx
  4973 00009E24 EBCD                <1> 	jmp	short get_env_string_compare
  4974                              <1> 
  4975                              <1> get_env_string_compare_not_ok:
  4976 00009E26 5F                  <1> 	pop	edi ; ***
  4977 00009E27 89DE                <1> 	mov	esi, ebx
  4978 00009E29 5B                  <1> 	pop	ebx ; **
  4979 00009E2A EBBA                <1> 	jmp	short get_env_string_stc_retn1
  4980                              <1> 
  4981                              <1> set_environment_string:
  4982                              <1> 	; 13/04/2016
  4983                              <1> 	; 12/04/2016
  4984                              <1> 	; 11/04/2016
  4985                              <1> 	; 06/04/2016
  4986                              <1> 	; 05/04/2016 (TRDOS 386 = TRDOS v2.0)
  4987                              <1> 	; 02/09/2011 (TRDOS v1, MAINPROG.ASM)
  4988                              <1> 	; 29/08/2011
  4989                              <1> 	; 29/08/2011
  4990                              <1> 	; INPUT->
  4991                              <1> 	;	ESI = ASCIIZ environment string
  4992                              <1> 	; OUTPUT ->
  4993                              <1> 	;	ESI is not changed
  4994                              <1> 	;	CF = 1 -> Could not set, 
  4995                              <1> 	;	     insufficient environment space
  4996                              <1> 	;
  4997                              <1> 	; (EAX, EDX will be changed) 
  4998                              <1> 	;
  4999                              <1> 	;    (EAX = Start address of the env string if > 0)	
  5000                              <1> 	;    (EDX = Environment string length)	
  5001                              <1> 
  5002 00009E2C 56                  <1> 	push 	esi ; *
  5003                              <1> 
  5004 00009E2D 31C0                <1> 	xor	eax, eax
  5005                              <1> 
  5006                              <1> set_env_chk_validation1:
  5007 00009E2F FEC4                <1> 	inc	ah ; variable (string) length
  5008 00009E31 AC                  <1> 	lodsb
  5009 00009E32 3C3D                <1> 	cmp	al, '='
  5010 00009E34 7415                <1> 	je	short set_env_chk_validation2
  5011 00009E36 3C20                <1> 	cmp	al, 20h
  5012 00009E38 720F                <1> 	jb	short set_env_string_stc
  5013                              <1> 
  5014                              <1> 	; 06/04/2016
  5015 00009E3A 3C61                <1> 	cmp	al, 'a'
  5016 00009E3C 72F1                <1> 	jb	short set_env_chk_validation1
  5017 00009E3E 3C7A                <1> 	cmp	al, 'z'
  5018 00009E40 77ED                <1> 	ja	short set_env_chk_validation1
  5019 00009E42 2C20                <1> 	sub	al, 'a'-'A'
  5020 00009E44 8846FF              <1> 	mov	[esi-1], al
  5021 00009E47 EBE6                <1> 	jmp	short set_env_chk_validation1
  5022                              <1> 
  5023                              <1> set_env_string_stc:
  5024 00009E49 5E                  <1> 	pop	esi ; *
  5025                              <1> 	;stc
  5026 00009E4A C3                  <1> 	retn 
  5027                              <1> 	   
  5028                              <1> set_env_chk_validation2:
  5029 00009E4B 51                  <1> 	push	ecx ; **
  5030 00009E4C 53                  <1> 	push	ebx ; *** 
  5031 00009E4D 57                  <1> 	push	edi ; ****
  5032                              <1> 
  5033                              <1> 	; 12/04/2016
  5034 00009E4E 8B5C240C            <1> 	mov	ebx, [esp+12]
  5035                              <1> 
  5036                              <1> set_env_chk_validation2w:
  5037 00009E52 89F7                <1> 	mov	edi, esi
  5038 00009E54 4F                  <1> 	dec	edi
  5039                              <1> 
  5040 00009E55 807FFF20            <1> 	cmp	byte [edi-1], 20h
  5041 00009E59 771A                <1> 	ja	short set_env_chk_validation2z
  5042                              <1> 	
  5043 00009E5B 56                  <1> 	push	esi
  5044 00009E5C 89FE                <1> 	mov	esi, edi
  5045 00009E5E 4E                  <1> 	dec	esi
  5046                              <1> 
  5047                              <1> set_env_chk_validation2x:
  5048 00009E5F 4E                  <1> 	dec	esi
  5049                              <1> 
  5050 00009E60 39DE                <1> 	cmp	esi, ebx
  5051 00009E62 7207                <1> 	jb	short set_env_chk_validation2y
  5052                              <1> 
  5053 00009E64 4F                  <1> 	dec	edi
  5054                              <1> 
  5055 00009E65 8A06                <1> 	mov	al, [esi]
  5056 00009E67 8807                <1> 	mov	[edi], al
  5057                              <1> 
  5058 00009E69 EBF4                <1> 	jmp	short set_env_chk_validation2x
  5059                              <1> 
  5060                              <1> set_env_chk_validation2y:
  5061 00009E6B 5E                  <1> 	pop	esi
  5062                              <1> 
  5063                              <1> 	;mov	byte [ebx], 20h
  5064                              <1> 	
  5065 00009E6C 43                  <1> 	inc 	ebx
  5066 00009E6D 895C240C            <1> 	mov	[esp+12], ebx
  5067                              <1> 
  5068 00009E71 FECC                <1> 	dec 	ah ; 13/04/2016
  5069                              <1> 
  5070 00009E73 EBDD                <1> 	jmp	short set_env_chk_validation2w
  5071                              <1> 	
  5072                              <1> set_env_chk_validation2z:	
  5073 00009E75 BA00300900          <1> 	mov	edx, Env_Page
  5074 00009E7A 89D7                <1> 	mov	edi, edx
  5075                              <1> 
  5076                              <1> set_env_chk_validation3:
  5077 00009E7C AC                  <1> 	lodsb
  5078 00009E7D 3C20                <1> 	cmp	al, 20h
  5079 00009E7F 74FB                <1> 	je	short set_env_chk_validation3
  5080                              <1> 
  5081 00009E81 9C                  <1> 	pushf
  5082                              <1> 
  5083                              <1> 	; 12/04/2016
  5084                              <1> set_env_chk_validation3n:
  5085 00009E82 3C61                <1> 	cmp	al, 'a'
  5086 00009E84 720C                <1> 	jb	short set_env_chk_validation3c
  5087 00009E86 3C7A                <1> 	cmp	al, 'z'
  5088 00009E88 7705                <1> 	ja	short set_env_chk_validation3x
  5089 00009E8A 2C20                <1> 	sub	al, 'a'-'A'
  5090 00009E8C 8846FF              <1> 	mov	[esi-1], al
  5091                              <1> 
  5092                              <1> set_env_chk_validation3x:
  5093 00009E8F AC                  <1> 	lodsb
  5094 00009E90 EBF0                <1> 	jmp	short set_env_chk_validation3n
  5095                              <1> 
  5096                              <1> set_env_chk_validation3c:
  5097 00009E92 3C20                <1> 	cmp	al, 20h
  5098 00009E94 73F9                <1> 	jnb	short set_env_chk_validation3x
  5099                              <1> 		
  5100 00009E96 803F00              <1> 	cmp	byte [edi], 0
  5101 00009E99 7731                <1> 	ja	short set_env_chk_validation4
  5102                              <1> 
  5103 00009E9B 9D                  <1> 	popf
  5104 00009E9C 7228                <1> 	jb	short set_env_string_nothing
  5105                              <1> 
  5106 00009E9E B900020000          <1> 	mov	ecx, Env_Page_Size ; 512 (4096)
  5107                              <1> 
  5108 00009EA3 89DE                <1> 	mov	esi, ebx ; 12/04/2016
  5109                              <1> 
  5110                              <1> set_env_string_copy_to_envb:
  5111 00009EA5 AC                  <1> 	lodsb
  5112 00009EA6 3C20                <1> 	cmp	al, 20h
  5113 00009EA8 720A                <1> 	jb	short set_env_string_copy_to_envb_z
  5114 00009EAA AA                  <1> 	stosb
  5115 00009EAB E2F8                <1> 	loop	set_env_string_copy_to_envb
  5116                              <1> 
  5117                              <1> 	; 11/04/2016
  5118 00009EAD 89D7                <1> 	mov	edi, edx ; Env_Page
  5119 00009EAF B900020000          <1> 	mov	ecx, Env_Page_Size 
  5120                              <1> 
  5121                              <1> set_env_string_copy_to_envb_z:
  5122 00009EB4 52                  <1> 	push	edx  ; Start address of the variable
  5123 00009EB5 BA00020000          <1> 	mov	edx, Env_Page_Size
  5124 00009EBA 29CA                <1> 	sub	edx, ecx ; variable (string) length
  5125                              <1> 
  5126 00009EBC 28C0                <1> 	sub	al, al ; 0
  5127 00009EBE F3AA                <1>  	rep	stosb ; clear remain bytes of the env page
  5128                              <1> 
  5129 00009EC0 58                  <1> 	pop	eax  ; Start address of the variable
  5130                              <1> 
  5131                              <1> set_env_string_allocate_envb_retn:  ; stc or clc return
  5132 00009EC1 5F                  <1> 	pop	edi ; ****
  5133 00009EC2 5B                  <1> 	pop	ebx ; ***
  5134 00009EC3 59                  <1> 	pop	ecx ; **
  5135 00009EC4 5E                  <1> 	pop	esi ; *	
  5136 00009EC5 C3                  <1> 	retn
  5137                              <1> 
  5138                              <1> set_env_string_nothing:
  5139 00009EC6 31C0                <1> 	xor	eax, eax
  5140 00009EC8 31D2                <1> 	xor	edx, edx ; 11/04/2016
  5141 00009ECA EBF5                <1> 	jmp	short set_env_string_allocate_envb_retn
  5142                              <1> 
  5143                              <1> set_env_chk_validation4:
  5144                              <1> 	; 11/04/2016
  5145 00009ECC 9D                  <1> 	popf
  5146                              <1> 
  5147 00009ECD 89D6                <1> 	mov	esi, edx  ; Env_Page
  5148                              <1> 
  5149                              <1> set_env_chk_validation5:	
  5150 00009ECF 89DF                <1> 	mov	edi, ebx  ; ASCIIZ environment string address	
  5151 00009ED1 0FB6CC              <1> 	movzx	ecx, ah ; Variable (string) length (with '=')
  5152                              <1> 
  5153                              <1> set_env_chk_validation5_loop:
  5154 00009ED4 AC                  <1> 	lodsb
  5155 00009ED5 AE                  <1> 	scasb
  5156 00009ED6 750A                <1> 	jne	short set_env_chk_validation6
  5157 00009ED8 E2FA                <1> 	loop	set_env_chk_validation5_loop
  5158                              <1> 
  5159 00009EDA 3C3D                <1> 	cmp	al, '='
  5160 00009EDC 0F8483000000        <1>         je      set_env_change_variable
  5161                              <1> 
  5162                              <1> set_env_chk_validation6:
  5163 00009EE2 08C0                <1> 	or	al, al ; 0
  5164 00009EE4 7403                <1> 	jz	short set_env_chk_validation7
  5165                              <1> 
  5166 00009EE6 AC                  <1> 	lodsb
  5167 00009EE7 EBF9                <1> 	jmp	short set_env_chk_validation6
  5168                              <1> 
  5169                              <1> set_env_chk_validation7:
  5170 00009EE9 88E1                <1> 	mov	cl, ah
  5171 00009EEB 01F1                <1> 	add	ecx, esi
  5172 00009EED 81F9FF310900        <1> 	cmp	ecx, Env_Page + Env_Page_Size - 1 
  5173                              <1> 		; 511 (4095) 
  5174                              <1> 		; strlen + '=' + 0
  5175 00009EF3 72DA                <1> 	jb	short set_env_chk_validation5
  5176                              <1> 
  5177                              <1> set_env_chk_validation8: ; variable not found
  5178 00009EF5 0FB6F4              <1> 	movzx	esi, ah  ; variable name length (with '=') 
  5179 00009EF8 01DE                <1> 	add	esi, ebx ; position just after of the '='
  5180                              <1> 
  5181                              <1> set_env_chk_validation8_loop:
  5182 00009EFA AC                  <1> 	lodsb
  5183 00009EFB 3C20                <1> 	cmp	al, 20h
  5184 00009EFD 74FB                <1> 	je	short set_env_chk_validation8_loop	
  5185 00009EFF 72C5                <1> 	jb	short set_env_string_nothing
  5186                              <1> 
  5187                              <1> set_env_chk_validation9:
  5188 00009F01 AC                  <1> 	lodsb
  5189 00009F02 3C20                <1> 	cmp	al, 20h
  5190 00009F04 73FB                <1> 	jnb	short set_env_chk_validation9
  5191                              <1> 
  5192                              <1> 	; End of ASCIIZ environment string
  5193                              <1> 
  5194                              <1> set_env_add_variable:
  5195 00009F06 29DE                <1> 	sub	esi, ebx ; variable+definition length
  5196                              <1> 	
  5197 00009F08 56                  <1> 	push	esi ; *****
  5198                              <1> 
  5199 00009F09 89D6                <1> 	mov	esi, edx ; Environment page address
  5200                              <1> 
  5201 00009F0B B900020000          <1> 	mov	ecx, Env_Page_Size ; 512 (4096)	
  5202                              <1> 
  5203                              <1> set_env_add_variable_loop:
  5204 00009F10 AC                  <1> 	lodsb
  5205 00009F11 20C0                <1> 	and	al, al		
  5206 00009F13 7406                <1> 	jz	short set_env_add_variable_chk1 ; 0
  5207 00009F15 E2F9                <1> 	loop	set_env_add_variable_loop
  5208                              <1> 
  5209                              <1> 	; 11/04/2016
  5210 00009F17 884EFF              <1> 	mov	[esi-1], cl ; 0
  5211 00009F1A 41                  <1> 	inc	ecx
  5212                              <1> 	
  5213                              <1> set_env_add_variable_chk1: 
  5214 00009F1B 49                  <1> 	dec	ecx
  5215 00009F1C 7408                <1> 	jz	short set_env_add_variable_nspc
  5216 00009F1E AC                  <1> 	lodsb
  5217 00009F1F 08C0                <1> 	or 	al, al
  5218 00009F21 740C                <1> 	jz	short set_env_add_variable_chk2 ; 00
  5219 00009F23 49                  <1> 	dec	ecx
  5220 00009F24 75EA                <1> 	jnz	short set_env_add_variable_loop
  5221                              <1> 
  5222                              <1> set_env_add_variable_nspc: ; no space on environment page
  5223 00009F26 58                  <1> 	pop	eax ; *****
  5224 00009F27 B808000000          <1> 	mov	eax, 8 ; No space for new environment string
  5225 00009F2C F9                  <1> 	stc
  5226 00009F2D EB92                <1>         jmp     short set_env_string_allocate_envb_retn
  5227                              <1> 
  5228                              <1> set_env_add_variable_chk2:
  5229 00009F2F 8B0C24              <1> 	mov	ecx, [esp] ; *****
  5230 00009F32 4E                  <1> 	dec	esi ; beginning address of the new variable
  5231 00009F33 89F0                <1> 	mov	eax, esi
  5232 00009F35 01C8                <1> 	add	eax, ecx ; string length (with CR)
  5233 00009F37 81C200020000        <1> 	add	edx, Env_Page_Size ; 512 (4096)
  5234 00009F3D 39D0                <1> 	cmp	eax, edx 
  5235 00009F3F 77E5                <1> 	ja	short set_env_add_variable_nspc
  5236 00009F41 49                  <1> 	dec	ecx ; except CR at the end
  5237 00009F42 89CA                <1> 	mov	edx, ecx ; 12/04/2016
  5238 00009F44 89F7                <1> 	mov	edi, esi
  5239 00009F46 893C24              <1> 	mov	[esp], edi ; ***** ; Start address of new variable
  5240 00009F49 89DE                <1> 	mov	esi, ebx ; ASCIIZ environment string address
  5241 00009F4B F3A4                <1> 	rep	movsb
  5242 00009F4D 28C0                <1> 	sub	al, al
  5243 00009F4F AA                  <1> 	stosb
  5244 00009F50 58                  <1> 	pop	eax ; ***** ; Beginning address of new variable			
  5245 00009F51 81FF00320900        <1>         cmp     edi, Env_Page + Env_Page_Size ; 12/04/2016
  5246 00009F57 0F8364FFFFFF        <1>         jnb     set_env_string_allocate_envb_retn ; OK !
  5247 00009F5D 880F                <1> 	mov	[edi], cl ; 0
  5248 00009F5F F8                  <1> 	clc	; 13/04/2016
  5249 00009F60 E95CFFFFFF          <1>         jmp     set_env_string_allocate_envb_retn ; OK !
  5250                              <1> 
  5251                              <1> set_env_change_variable:
  5252                              <1> 	; 06/04/2016
  5253                              <1> 	; esi = Variable's address in environment page (after '=')
  5254                              <1> 	; edi = ASCIIZ environment string address (after '=')
  5255                              <1> 
  5256                              <1> 	; ah = variable length from start to the '='
  5257 00009F65 8825[B06A0100]      <1> 	mov	[env_var_length], ah
  5258                              <1> 
  5259 00009F6B 28C9                <1> 	sub	cl, cl ; ecx = 0
  5260                              <1> 
  5261 00009F6D 57                  <1> 	push	edi ; *****
  5262                              <1> 
  5263 00009F6E 89F7                <1> 	mov	edi, esi ; 11/04/2016
  5264                              <1> 
  5265                              <1> set_env_change_variable_calc1:
  5266 00009F70 AC                  <1> 	lodsb
  5267 00009F71 08C0                <1> 	or	al, al
  5268 00009F73 7403                <1> 	jz	short set_env_change_variable_calc2
  5269                              <1> 
  5270 00009F75 41                  <1> 	inc	ecx ; length of environment string (after the '=')
  5271                              <1> 
  5272 00009F76 EBF8                <1> 	jmp	short set_env_change_variable_calc1	
  5273                              <1> 
  5274                              <1> set_env_change_variable_calc2:
  5275 00009F78 8B3424              <1> 	mov	esi, [esp] ; ASCIIZ environment string address
  5276                              <1> 	
  5277 00009F7B 29D2                <1> 	sub	edx, edx
  5278                              <1> 
  5279                              <1> set_env_change_variable_calc3:
  5280 00009F7D AC                  <1> 	lodsb
  5281 00009F7E 3C20                <1> 	cmp	al, 20h
  5282 00009F80 7203                <1> 	jb	short set_env_change_variable_calc4
  5283                              <1> 
  5284 00009F82 42                  <1> 	inc	edx ; length of ASCIIZ string (after the '=')
  5285                              <1> 	
  5286 00009F83 EBF8                <1> 	jmp	short set_env_change_variable_calc3
  5287                              <1> 	
  5288                              <1> set_env_change_variable_calc4:
  5289 00009F85 C646FF00            <1> 	mov	byte [esi-1], 0  ; put ZERO instead of CR
  5290                              <1> 	
  5291 00009F89 5E                  <1> 	pop	esi ; ***** ; ASCIIZ string address (after '=')
  5292                              <1> 
  5293                              <1> 	; EDI = Old variable's address (after '=')
  5294                              <1> 	
  5295                              <1> 	; compare the new string with the old string
  5296 00009F8A 39CA                <1> 	cmp	edx, ecx
  5297 00009F8C 7717                <1> 	ja	short set_env_change_variable_calc5 ; longer
  5298 00009F8E 0F828F000000        <1>         jb      set_env_change_variable_calc9 ; shorter
  5299                              <1> 	
  5300                              <1> 	;same length (simple copy)
  5301 00009F94 0FB6C4              <1> 	movzx	eax, ah
  5302 00009F97 01C2                <1> 	add	edx, eax
  5303 00009F99 F7D8                <1> 	neg	eax
  5304 00009F9B 01F8                <1> 	add	eax, edi
  5305                              <1> 	; EAX = Start address of the variable
  5306                              <1> 	; EDX = Variable length (without ZERO at the end of variable)
  5307                              <1> 
  5308 00009F9D F3A4                <1> 	rep	movsb
  5309 00009F9F F8                  <1> 	clc	; 13/04/2016
  5310 00009FA0 E91CFFFFFF          <1>         jmp     set_env_string_allocate_envb_retn ; OK !
  5311                              <1> 
  5312                              <1> set_env_change_variable_calc5:
  5313                              <1> 	; 11/04/2016
  5314 00009FA5 52                  <1> 	push	edx ; *****
  5315 00009FA6 29CA                <1> 	sub	edx, ecx ; difference ; (the new string is longer)
  5316 00009FA8 89F3                <1> 	mov 	ebx, esi
  5317 00009FAA 89FE                <1> 	mov	esi, edi
  5318                              <1> 
  5319                              <1> set_env_change_variable_calc6:
  5320 00009FAC AC                  <1> 	lodsb 
  5321 00009FAD 20C0                <1> 	and	al, al
  5322 00009FAF 75FB                <1> 	jnz	short set_env_change_variable_calc6
  5323                              <1> 
  5324 00009FB1 81FE00320900        <1> 	cmp	esi, Env_Page + Env_Page_Size ; 512 (4096)
  5325 00009FB7 0F8369FFFFFF        <1>         jnb     set_env_add_variable_nspc
  5326                              <1> 
  5327 00009FBD 89F9                <1> 	mov	ecx, edi  ; current (old) variable's address
  5328 00009FBF 89F7                <1> 	mov	edi, esi  ; next variable's address 
  5329                              <1> 
  5330 00009FC1 AC                  <1> 	lodsb
  5331 00009FC2 08C0                <1> 	or	al, al
  5332 00009FC4 7416                <1> 	jz	short set_env_change_variable_calc8 ; 00
  5333                              <1> 
  5334                              <1> set_env_change_variable_calc7:
  5335 00009FC6 AC                  <1> 	lodsb
  5336 00009FC7 20C0                <1> 	and	al, al
  5337 00009FC9 75FB                <1> 	jnz	short set_env_change_variable_calc7
  5338                              <1> 
  5339 00009FCB 81FE00320900        <1> 	cmp	esi, Env_Page + Env_Page_Size ; 512 (4096)
  5340 00009FD1 0F834FFFFFFF        <1>         jnb     set_env_add_variable_nspc
  5341                              <1> 
  5342 00009FD7 AC                  <1> 	lodsb
  5343 00009FD8 08C0                <1> 	or	al, al
  5344 00009FDA 75EA                <1> 	jnz	short set_env_change_variable_calc7
  5345                              <1> 
  5346                              <1> set_env_change_variable_calc8:
  5347 00009FDC 4E                  <1> 	dec	esi ; address of the second (last) 0 of the 00
  5348                              <1> 
  5349 00009FDD 01F2                <1> 	add	edx, esi ; final position of the last 0
  5350                              <1> 
  5351 00009FDF 81FA00320900        <1> 	cmp	edx, Env_Page + Env_Page_Size ; 512 (4096)
  5352 00009FE5 0F833BFFFFFF        <1>         jnb     set_env_add_variable_nspc
  5353                              <1> 
  5354 00009FEB 89C8                <1> 	mov	eax, ecx ; old variable's address (after '=')
  5355                              <1> 
  5356 00009FED 89F1                <1> 	mov	ecx, esi 
  5357 00009FEF 29F9                <1> 	sub	ecx, edi ; count of bytes to move forward
  5358                              <1> 
  5359                              <1> 	; 13/04/2016
  5360 00009FF1 C60200              <1> 	mov	byte [edx], 0
  5361 00009FF4 89D7                <1> 	mov	edi, edx
  5362 00009FF6 29F2                <1> 	sub	edx, esi ; difference (additional byte count)
  5363 00009FF8 4F                  <1> 	dec	edi ; the last zero address (first byte of the 00)
  5364 00009FF9 89FE                <1> 	mov	esi, edi
  5365 00009FFB 29D6                <1> 	sub	esi, edx ; - displacement
  5366                              <1> 	
  5367 00009FFD FA                  <1> 	cli	; disable interrupts
  5368 00009FFE FD                  <1> 	std	; backward
  5369                              <1> 
  5370 00009FFF F3A4                <1> 	rep	movsb ; move ECX bytes from DS:ESI to ES:EDI
  5371                              <1> 
  5372 0000A001 FC                  <1> 	cld	; forward (default)
  5373 0000A002 FB                  <1> 	sti	; enable interrupts
  5374                              <1> 	
  5375 0000A003 89C7                <1> 	mov	edi, eax
  5376 0000A005 59                  <1> 	pop	ecx ; ***** ; byte count (after '=')
  5377 0000A006 89CA                <1> 	mov	edx, ecx
  5378 0000A008 89DE                <1> 	mov	esi, ebx ; ASCIIZ string address (after '=')
  5379 0000A00A 89FB                <1> 	mov	ebx, edi
  5380                              <1> 
  5381 0000A00C F3A4                <1> 	rep	movsb
  5382                              <1> 
  5383 0000A00E 880F                <1> 	mov	[edi], cl ; 0 ; end of variable
  5384                              <1> 
  5385 0000A010 0FB605[B06A0100]    <1> 	movzx	eax, byte [env_var_length]
  5386 0000A017 01C2                <1> 	add	edx, eax ; variable length (total)
  5387 0000A019 F7D8                <1> 	neg	eax
  5388 0000A01B 01D8                <1> 	add	eax, ebx ; start address of the variable
  5389 0000A01D F8                  <1> 	clc	; 13/04/2016
  5390 0000A01E E99EFEFFFF          <1>         jmp     set_env_string_allocate_envb_retn ; OK !
  5391                              <1> 
  5392                              <1> set_env_change_variable_calc9:
  5393                              <1> 	; 11/04/2016
  5394 0000A023 21D2                <1> 	and	edx, edx ; is empty ?
  5395 0000A025 753B                <1> 	jnz	short set_env_change_variable_calc15
  5396                              <1> 	
  5397 0000A027 0FB6DC              <1> 	movzx	ebx, ah
  5398 0000A02A F7DB                <1> 	neg	ebx
  5399 0000A02C 01FB                <1> 	add	ebx, edi
  5400                              <1> 
  5401                              <1> 	; EBX = Start address of the variable (in env page)
  5402                              <1> 	; EDX = Variable length = 0
  5403                              <1> 	
  5404 0000A02E 89FE                <1> 	mov	esi, edi
  5405                              <1> 
  5406                              <1> set_env_change_variable_calc10:
  5407 0000A030 AC                  <1> 	lodsb
  5408 0000A031 08C0                <1> 	or	al, al
  5409 0000A033 75FB                <1> 	jnz	short set_env_change_variable_calc10
  5410                              <1> 
  5411 0000A035 B9FF310900          <1> 	mov	ecx, Env_Page + Env_Page_Size - 1
  5412                              <1> 
  5413 0000A03A 39CE                <1> 	cmp	esi, ecx ; +511 (+4095)
  5414 0000A03C 7604                <1> 	jna	short set_env_change_variable_calc11
  5415                              <1> 
  5416 0000A03E 89CE                <1> 	mov	esi, ecx
  5417 0000A040 8806                <1> 	mov	[esi], al ; 0
  5418                              <1> 
  5419                              <1> set_env_change_variable_calc11:
  5420 0000A042 89DF                <1> 	mov	edi, ebx ; old variable's start address
  5421                              <1> 
  5422                              <1> set_env_change_variable_calc12:
  5423 0000A044 AC                  <1> 	lodsb
  5424 0000A045 AA                  <1> 	stosb
  5425 0000A046 20C0                <1> 	and	al, al
  5426 0000A048 75FA                <1> 	jnz	short set_env_change_variable_calc12
  5427 0000A04A 39CE                <1> 	cmp	esi, ecx
  5428 0000A04C 7706                <1> 	ja	short set_env_change_variable_calc13
  5429 0000A04E AC                  <1> 	lodsb
  5430 0000A04F AA                  <1> 	stosb
  5431 0000A050 20C0                <1> 	and	al, al
  5432 0000A052 75F0                <1> 	jnz	short set_env_change_variable_calc12	
  5433                              <1> 
  5434                              <1> set_env_change_variable_calc13:
  5435 0000A054 29F9                <1> 	sub	ecx, edi
  5436 0000A056 7203                <1> 	jb	short set_env_change_variable_calc14
  5437 0000A058 41                  <1> 	inc	ecx ; 1-512 (1-4096)
  5438 0000A059 F3AA                <1> 	rep	stosb ; al = 0	
  5439                              <1> 
  5440                              <1> set_env_change_variable_calc14:
  5441 0000A05B 29C0                <1> 	sub	eax, eax ; Start address of the variable
  5442                              <1> 	; EAX = 0 -> Variable is removed
  5443                              <1> 	; EDX = Variable length = 0	
  5444                              <1> 
  5445 0000A05D E95FFEFFFF          <1>         jmp     set_env_string_allocate_envb_retn ; OK !
  5446                              <1> 	    
  5447                              <1> set_env_change_variable_calc15:	
  5448 0000A062 52                  <1> 	push	edx ; *****
  5449 0000A063 F7DA                <1> 	neg	edx
  5450 0000A065 01CA                <1> 	add	edx, ecx ; difference (the old string is longer)
  5451 0000A067 89F3                <1> 	mov 	ebx, esi
  5452 0000A069 89FE                <1> 	mov	esi, edi
  5453                              <1> 
  5454                              <1> set_env_change_variable_calc16:
  5455 0000A06B AC                  <1> 	lodsb 
  5456 0000A06C 20C0                <1> 	and	al, al
  5457 0000A06E 75FB                <1> 	jnz	short set_env_change_variable_calc16
  5458                              <1> 
  5459 0000A070 B900320900          <1> 	mov	ecx, Env_Page + Env_Page_Size
  5460                              <1> 
  5461 0000A075 39CE                <1> 	cmp	esi, ecx ; +512 (+4096)
  5462 0000A077 7605                <1> 	jna	short set_env_change_variable_calc17
  5463                              <1> 
  5464 0000A079 89CE                <1> 	mov	esi, ecx
  5465 0000A07B 8846FF              <1> 	mov	[esi-1], al ; 0
  5466                              <1> 
  5467                              <1> set_env_change_variable_calc17:
  5468 0000A07E 89F9                <1> 	mov	ecx, edi  ; current (old) variable's address
  5469 0000A080 89F7                <1> 	mov	edi, esi  ; next variable's address 
  5470                              <1> 
  5471 0000A082 AC                  <1> 	lodsb
  5472 0000A083 08C0                <1> 	or	al, al
  5473 0000A085 741D                <1> 	jz	short set_env_change_variable_calc20
  5474                              <1> 
  5475                              <1> set_env_change_variable_calc18:
  5476 0000A087 AC                  <1> 	lodsb
  5477 0000A088 20C0                <1> 	and	al, al
  5478 0000A08A 75FB                <1> 	jnz	short set_env_change_variable_calc18
  5479                              <1> 
  5480 0000A08C 81FE00320900        <1> 	cmp	esi, Env_Page + Env_Page_Size
  5481 0000A092 720B                <1> 	jb	short set_env_change_variable_calc19
  5482 0000A094 740E                <1> 	je	short set_env_change_variable_calc20
  5483                              <1> 
  5484 0000A096 BEFF310900          <1> 	mov	esi, Env_Page + Env_Page_Size - 1
  5485 0000A09B 8806                <1> 	mov	[esi], al ; 0
  5486 0000A09D EB06                <1> 	jmp	short set_env_change_variable_calc21
  5487                              <1> 
  5488                              <1> set_env_change_variable_calc19:
  5489 0000A09F AC                  <1> 	lodsb
  5490 0000A0A0 08C0                <1> 	or	al, al
  5491 0000A0A2 75E3                <1> 	jnz	short set_env_change_variable_calc18
  5492                              <1> 
  5493                              <1> set_env_change_variable_calc20:
  5494 0000A0A4 4E                  <1> 	dec	esi ; address of the second (last) 0 of the 00
  5495                              <1> 
  5496                              <1> set_env_change_variable_calc21:
  5497                              <1> 	; edx = difference (byte count)
  5498                              <1> 	
  5499 0000A0A5 89C8                <1> 	mov	eax, ecx ; old variable's address (after '=')
  5500                              <1> 
  5501 0000A0A7 89F1                <1> 	mov	ecx, esi 
  5502 0000A0A9 29F9                <1> 	sub	ecx, edi ; count of bytes to move backward
  5503                              <1> 
  5504 0000A0AB 89FE                <1> 	mov	esi, edi ; next variable's address
  5505 0000A0AD 29D7                <1> 	sub	edi, edx ; (displacement)
  5506                              <1> 	
  5507 0000A0AF F3A4                <1> 	rep	movsb
  5508                              <1> 
  5509 0000A0B1 880F                <1> 	mov	[edi], cl ; 0 ; 00 ; end of environment variables
  5510                              <1> 
  5511 0000A0B3 89C7                <1> 	mov	edi, eax
  5512 0000A0B5 5A                  <1> 	pop	edx ; ***** ; byte count (after '=')
  5513 0000A0B6 89D1                <1> 	mov	ecx, edx
  5514 0000A0B8 89DE                <1> 	mov	esi, ebx ; ASCIIZ string address (after '=')
  5515 0000A0BA 89FB                <1> 	mov	ebx, edi
  5516                              <1> 	
  5517 0000A0BC F3A4                <1> 	rep	movsb
  5518                              <1> 
  5519 0000A0BE 880F                <1> 	mov	[edi], cl ; 0 ; end of variable
  5520                              <1> 
  5521 0000A0C0 0FB605[B06A0100]    <1> 	movzx	eax, byte [env_var_length]
  5522 0000A0C7 01C2                <1> 	add	edx, eax ; variable length (total)
  5523 0000A0C9 F7D8                <1> 	neg	eax
  5524 0000A0CB 01D8                <1> 	add	eax, ebx ; start address of the variable
  5525 0000A0CD F8                  <1> 	clc	; 13/04/2016
  5526 0000A0CE E9EEFDFFFF          <1>         jmp     set_env_string_allocate_envb_retn ; OK !
  5527                              <1> 
  5528                              <1> mainprog_startup_configuration:
  5529                              <1> 	; 22/11/2017
  5530                              <1> 	; 06/05/2016
  5531                              <1> 	; 14/04/2016 (TRDOS 386 = TRDOS v2.0)
  5532                              <1> 	; 17/09/2011 (TRDOS v1, MAINPROG.ASM)
  5533                              <1> 	;
  5534                              <1> loc_load_mainprog_cfg_file:
  5535 0000A0D3 BE[0D130100]        <1> 	mov	esi, MainProgCfgFile
  5536 0000A0D8 66B80018            <1> 	mov	ax, 1800h ; Except volume label and dirs
  5537 0000A0DC E83EEAFFFF          <1> 	call	find_first_file
  5538 0000A0E1 7256                <1> 	jc	short loc_load_mainprog_cfg_exit
  5539                              <1> 
  5540                              <1> 	;or	eax, eax
  5541                              <1> 	;jz	short loc_load_mainprog_cfg_exit
  5542                              <1> 
  5543                              <1> loc_start_mainprog_configuration:
  5544                              <1> 	; ESI = FindFile_DirEntry Location
  5545                              <1> 	; EAX = File Size
  5546                              <1> 
  5547 0000A0E3 A3[345F0100]        <1> 	mov	[MainProgCfg_FileSize], eax
  5548                              <1> 
  5549 0000A0E8 668B5614            <1> 	mov	dx, [esi+DirEntry_FstClusHI]
  5550 0000A0EC C1E210              <1> 	shl	edx, 16
  5551 0000A0EF 668B561A            <1> 	mov	dx, [esi+DirEntry_FstClusLO]
  5552 0000A0F3 8915[646A0100]      <1> 	mov	[csftdf_sf_cluster], edx
  5553                              <1> 
  5554 0000A0F9 89C1                <1> 	mov	ecx, eax
  5555 0000A0FB 29C0                <1> 	sub	eax, eax
  5556                              <1> 
  5557                              <1> 	; TRDOS 386 (TRDOS v2.0)
  5558                              <1> 	; Allocate contiguous memory block for loading the file
  5559                              <1> 	
  5560                              <1> 	; eax = 0 (Allocate memory from the beginning)
  5561                              <1> 	; ecx = File (Allocation) size in bytes
  5562                              <1> 	
  5563 0000A0FD E88DBAFFFF          <1> 	call	allocate_memory_block
  5564 0000A102 7235                <1> 	jc	short loc_load_mainprog_cfg_exit
  5565                              <1> 
  5566 0000A104 A3[5C6A0100]        <1> 	mov	[csftdf_sf_mem_addr], eax ; loading address
  5567 0000A109 890D[606A0100]      <1> 	mov	[csftdf_sf_mem_bsize], ecx ; block size
  5568                              <1> 
  5569 0000A10F 31DB                <1> 	xor	ebx, ebx
  5570                              <1> 	;mov	[csftdf_sf_rbytes], ebx ; 0, reset
  5571                              <1> 
  5572 0000A111 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv] ; [FindFile_Drv]
  5573 0000A117 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  5574 0000A11C 01DE                <1> 	add	esi, ebx
  5575                              <1> 
  5576 0000A11E 8B1D[5C6A0100]      <1> 	mov	ebx, [csftdf_sf_mem_addr] ; memory block address
  5577                              <1> 
  5578 0000A124 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  5579 0000A128 7710                <1>         ja	short loc_mcfg_load_fat_file
  5580                              <1> 
  5581 0000A12A C705[6C6A0100]0000- <1> 	mov	dword [csftdf_r_size], 65536
  5581 0000A132 0100                <1>
  5582 0000A134 E9A1010000          <1>         jmp     loc_mcfg_load_fs_file
  5583                              <1> 
  5584                              <1> loc_load_mainprog_cfg_exit:
  5585 0000A139 C3                  <1> 	retn 
  5586                              <1> 
  5587                              <1> loc_mcfg_load_fat_file:
  5588 0000A13A 0FB74611            <1> 	movzx	eax, word [esi+LD_BPB+BytesPerSec]
  5589 0000A13E 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+SecPerClust]
  5590 0000A142 F7E1                <1> 	mul	ecx
  5591 0000A144 A3[6C6A0100]        <1> 	mov	[csftdf_r_size], eax
  5592                              <1> 
  5593                              <1> loc_mcfg_load_fat_file_next:
  5594 0000A149 E822010000          <1> 	call	mcfg_read_fat_file_sectors
  5595 0000A14E 0F8206010000        <1>         jc      mcfg_deallocate_mem
  5596                              <1> 
  5597 0000A154 09D2                <1> 	or	edx, edx ; edx > 0 -> EOF
  5598 0000A156 74F1                <1> 	jz	short loc_mcfg_load_fat_file_next
  5599                              <1> 
  5600                              <1> loc_mcfg_load_fat_file_ok:
  5601                              <1> 	; 06/05/2016
  5602 0000A158 C705[006B0100]-     <1> 	mov	dword [mainprog_return_addr], loc_mcfg_ci_return_addr 
  5602 0000A15E [1BA20000]          <1>
  5603                              <1> 	;
  5604 0000A162 8B35[5C6A0100]      <1> 	mov	esi, [csftdf_sf_mem_addr]
  5605 0000A168 8935[385F0100]      <1> 	mov	[MainProgCfg_LineOffset], esi
  5606                              <1> 	
  5607 0000A16E A1[345F0100]        <1> 	mov	eax, [MainProgCfg_FileSize]
  5608 0000A173 89C2                <1> 	mov	edx, eax
  5609 0000A175 01F2                <1> 	add	edx, esi
  5610                              <1> 
  5611                              <1> loc_mcfg_process_next_line_check:
  5612 0000A177 89C1                <1> 	mov	ecx, eax
  5613                              <1> 
  5614 0000A179 803E2A              <1> 	cmp	byte [esi], "*" ; Remark sign
  5615 0000A17C 7503                <1> 	jne	short loc_mcfg_process_next_line
  5616 0000A17E 46                  <1> 	inc	esi
  5617 0000A17F EB17                <1> 	jmp	short loc_move_mainprog_cfg_nl1
  5618                              <1> 
  5619                              <1> loc_mcfg_process_next_line:
  5620 0000A181 83F94F              <1> 	cmp	ecx, 79
  5621 0000A184 7605                <1> 	jna	short loc_start_mainprog_cfg_process
  5622                              <1> 	
  5623 0000A186 B94F000000          <1> 	mov	ecx, 79 
  5624                              <1> 
  5625                              <1> loc_start_mainprog_cfg_process:
  5626 0000A18B BF[F65F0100]        <1> 	mov	edi, CommandBuffer
  5627                              <1> 
  5628                              <1> loc_move_mainprog_cfg_line:
  5629 0000A190 AC                  <1> 	lodsb
  5630 0000A191 3C20                <1> 	cmp	al, 20h
  5631 0000A193 720C                <1> 	jb	short loc_move_mainprog_cfg_nl2
  5632 0000A195 AA                  <1> 	stosb
  5633 0000A196 E2F8                <1> 	loop	loc_move_mainprog_cfg_line
  5634                              <1> 
  5635                              <1> loc_move_mainprog_cfg_nl1:
  5636 0000A198 39D6                <1> 	cmp	esi, edx ; + configuration file size
  5637 0000A19A 7312                <1> 	jnb	short loc_end_of_mainprog_cfg_line
  5638 0000A19C AC                  <1> 	lodsb
  5639 0000A19D 3C20                <1> 	cmp	al, 20h
  5640 0000A19F 73F7                <1> 	jnb	short loc_move_mainprog_cfg_nl1
  5641                              <1> 
  5642                              <1> loc_move_mainprog_cfg_nl2:
  5643 0000A1A1 39D6                <1> 	cmp	esi, edx
  5644 0000A1A3 7309                <1> 	jnb	short loc_end_of_mainprog_cfg_line
  5645 0000A1A5 8A06                <1> 	mov	al, [esi]
  5646 0000A1A7 3C20                <1> 	cmp	al, 20h
  5647 0000A1A9 7703                <1>  	ja	short loc_end_of_mainprog_cfg_line
  5648 0000A1AB 46                  <1> 	inc	esi
  5649 0000A1AC EBF3                <1> 	jmp	short loc_move_mainprog_cfg_nl2	               
  5650                              <1> 
  5651                              <1> loc_end_of_mainprog_cfg_line:
  5652 0000A1AE C60700              <1> 	mov	byte [edi], 0
  5653                              <1> 
  5654 0000A1B1 8935[385F0100]      <1> 	mov	[MainProgCfg_LineOffset], esi
  5655                              <1> 
  5656                              <1> 	; 22/11/2017
  5657 0000A1B7 BE[FE5F0100]        <1> 	mov	esi, CommandBuffer + 8
  5658 0000A1BC 29FE                <1> 	sub	esi, edi
  5659 0000A1BE 7606                <1> 	jna	short loc_move_mainprog_cfg_command
  5660 0000A1C0 30C0                <1> 	xor	al, al
  5661                              <1> loc_mainprog_cfg_clear_chrs:
  5662 0000A1C2 AA                  <1> 	stosb
  5663 0000A1C3 4E                  <1> 	dec	esi
  5664 0000A1C4 75FC                <1> 	jnz	short loc_mainprog_cfg_clear_chrs	
  5665                              <1> 
  5666                              <1> loc_move_mainprog_cfg_command:
  5667 0000A1C6 BE[F65F0100]        <1> 	mov	esi, CommandBuffer
  5668 0000A1CB 89F7                <1> 	mov	edi, esi
  5669 0000A1CD 31DB                <1> 	xor	ebx, ebx
  5670                              <1> 	;xor	ecx, ecx
  5671 0000A1CF 30C9                <1> 	xor	cl, cl
  5672                              <1> 
  5673                              <1> loc_move_mcfg_first_cmd_char:
  5674 0000A1D1 8A041E              <1> 	mov	al, [esi+ebx]
  5675 0000A1D4 FEC3                <1> 	inc	bl 
  5676 0000A1D6 3C20                <1> 	cmp	al, 20h
  5677 0000A1D8 7712                <1> 	ja	short loc_move_mcfg_cmd_capitalizing
  5678 0000A1DA 7237                <1> 	jb	short loc_move_mcfg_cmd_arguments_ok
  5679 0000A1DC 80FB4F              <1> 	cmp	bl, 79
  5680 0000A1DF 72F0                <1> 	jb	short loc_move_mcfg_first_cmd_char
  5681 0000A1E1 EB30                <1> 	jmp	short loc_move_mcfg_cmd_arguments_ok
  5682                              <1> 
  5683                              <1> loc_move_mcfg_next_cmd_char:
  5684 0000A1E3 8A041E              <1> 	mov	al, [esi+ebx]
  5685 0000A1E6 FEC3                <1> 	inc	bl
  5686 0000A1E8 3C20                <1> 	cmp	al, 20h
  5687 0000A1EA 7614                <1> 	jna	short loc_move_mcfg_cmd_ok
  5688                              <1> 
  5689                              <1> loc_move_mcfg_cmd_capitalizing:
  5690 0000A1EC 3C61                <1> 	cmp	al, 61h ; 'a'
  5691 0000A1EE 7206                <1> 	jb	short loc_move_mcfg_cmd_caps_ok
  5692 0000A1F0 3C7A                <1> 	cmp	al, 7Ah ; 'z'
  5693 0000A1F2 7702                <1> 	ja	short loc_move_mcfg_cmd_caps_ok
  5694 0000A1F4 24DF                <1> 	and	al, 0DFh ; sub	al, 'a'-'A'
  5695                              <1> 
  5696                              <1> loc_move_mcfg_cmd_caps_ok:
  5697 0000A1F6 AA                  <1> 	stosb 
  5698 0000A1F7 FEC1                <1> 	inc	cl
  5699 0000A1F9 80FB4F              <1> 	cmp	bl, 79
  5700 0000A1FC 72E5                <1> 	jb	short loc_move_mcfg_next_cmd_char
  5701 0000A1FE EB13                <1> 	jmp	short loc_move_mcfg_cmd_arguments_ok
  5702                              <1> 
  5703                              <1> loc_move_mcfg_cmd_ok:
  5704 0000A200 30C0                <1> 	xor	al, al ; 0
  5705                              <1> 
  5706                              <1> loc_move_mcfg_cmd_arguments:
  5707 0000A202 8807                <1> 	mov	[edi], al
  5708 0000A204 47                  <1> 	inc	edi
  5709 0000A205 80FB4F              <1> 	cmp	bl, 79
  5710 0000A208 7309                <1> 	jnb	short loc_move_mcfg_cmd_arguments_ok
  5711 0000A20A 8A041E              <1> 	mov	al, [esi+ebx]
  5712 0000A20D FEC3                <1> 	inc	bl
  5713 0000A20F 3C20                <1> 	cmp	al, 20h
  5714 0000A211 73EF                <1> 	jnb	short loc_move_mcfg_cmd_arguments
  5715                              <1> 	
  5716                              <1> loc_move_mcfg_cmd_arguments_ok:
  5717 0000A213 C60700              <1> 	mov	byte [edi], 0
  5718                              <1>        
  5719                              <1> loc_mcfg_process_cmd_interpreter:
  5720 0000A216 E825E0FFFF          <1> 	call    command_interpreter
  5721                              <1> 
  5722                              <1> loc_mcfg_ci_return_addr: 
  5723 0000A21B A1[345F0100]        <1> 	mov	eax, [MainProgCfg_FileSize]
  5724 0000A220 89C2                <1> 	mov	edx, eax
  5725 0000A222 8B35[385F0100]      <1> 	mov	esi, [MainProgCfg_LineOffset]
  5726 0000A228 01F2                <1> 	add	edx, esi
  5727 0000A22A 0305[5C6A0100]      <1> 	add	eax, [csftdf_sf_mem_addr]
  5728 0000A230 29F0                <1> 	sub	eax, esi
  5729 0000A232 0F873FFFFFFF        <1>         ja      loc_mcfg_process_next_line_check
  5730                              <1> 
  5731 0000A238 E81D000000          <1> 	call	mcfg_deallocate_mem
  5732                              <1>  
  5733 0000A23D B94F000000          <1>  	mov	ecx, 79 ; 80 ?
  5734 0000A242 BF[F65F0100]        <1> 	mov	edi, CommandBuffer
  5735 0000A247 30C0                <1> 	xor	al, al
  5736 0000A249 F3AA                <1> 	rep	stosb
  5737                              <1> 
  5738                              <1> 	; 06/05/2016
  5739 0000A24B BE[631F0100]        <1> 	mov	esi, nextline
  5740 0000A250 E8B0C9FFFF          <1> 	call	print_msg
  5741 0000A255 E963D6FFFF          <1> 	jmp	dos_prompt
  5742                              <1> 
  5743                              <1> mcfg_deallocate_mem:
  5744 0000A25A A1[5C6A0100]        <1> 	mov	eax, [csftdf_sf_mem_addr] ; start address
  5745 0000A25F 8B0D[606A0100]      <1> 	mov	ecx, [csftdf_sf_mem_bsize] ; block size	
  5746                              <1> 	;call	deallocate_memory_block
  5747                              <1> 	;retn
  5748 0000A265 E932BBFFFF          <1> 	jmp	deallocate_memory_block
  5749                              <1> 
  5750                              <1> mcfg_read_file_sectors:
  5751                              <1> 	; 14/04/2016
  5752 0000A26A 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  5753 0000A26E 7669                <1>         jna	short mcfg_read_fs_file_sectors
  5754                              <1> 
  5755                              <1> mcfg_read_fat_file_sectors:
  5756                              <1> 	; return:
  5757                              <1> 	;   CF = 0 & EDX > 0 -> END OF FILE
  5758                              <1> 	;   CF = 0 & EDX = 0 -> not EOF
  5759                              <1> 	;   CF = 1 -> read error (error code in AL)	
  5760                              <1> 
  5761                              <1> mcfg_read_fat_file_secs_0:
  5762 0000A270 8B15[345F0100]      <1> 	mov	edx, [MainProgCfg_FileSize]
  5763 0000A276 2B15[746A0100]      <1> 	sub	edx, [csftdf_sf_rbytes]
  5764 0000A27C 3B15[6C6A0100]      <1> 	cmp	edx, [csftdf_r_size]	
  5765 0000A282 7306                <1> 	jnb	short mcfg_read_fat_file_secs_1
  5766 0000A284 8915[6C6A0100]      <1> 	mov	[csftdf_r_size], edx
  5767                              <1> 		
  5768                              <1> mcfg_read_fat_file_secs_1:
  5769 0000A28A A1[6C6A0100]        <1> 	mov	eax, [csftdf_r_size]
  5770 0000A28F 29D2                <1> 	sub	edx, edx
  5771 0000A291 0FB74E11            <1> 	movzx	ecx, word [esi+LD_BPB+BytesPerSec]
  5772 0000A295 01C8                <1> 	add	eax, ecx
  5773 0000A297 48                  <1> 	dec	eax
  5774 0000A298 F7F1                <1> 	div	ecx
  5775 0000A29A 89C1                <1> 	mov	ecx, eax ; sector count
  5776 0000A29C A1[646A0100]        <1> 	mov	eax, [csftdf_sf_cluster]
  5777                              <1> 
  5778                              <1> 	; EBX = memory block address (current)
  5779                              <1> 	
  5780 0000A2A1 E88C230000          <1> 	call	read_fat_file_sectors
  5781 0000A2A6 7230                <1> 	jc	short mcfg_read_fat_file_secs_3
  5782                              <1> 
  5783                              <1> 	; EBX = next memory address
  5784                              <1> 
  5785 0000A2A8 A1[746A0100]        <1> 	mov	eax, [csftdf_sf_rbytes]
  5786 0000A2AD 0305[6C6A0100]      <1> 	add	eax, [csftdf_r_size]
  5787 0000A2B3 8B15[345F0100]      <1> 	mov	edx, [MainProgCfg_FileSize]
  5788 0000A2B9 39D0                <1> 	cmp	eax, edx
  5789 0000A2BB 731B                <1> 	jnb	short mcfg_read_fat_file_secs_3 ; edx > 0
  5790 0000A2BD A3[746A0100]        <1> 	mov	[csftdf_sf_rbytes], eax
  5791                              <1> 
  5792 0000A2C2 53                  <1> 	push	ebx ; *
  5793                              <1> 	; get next cluster (csftdf_r_size! bytes)
  5794 0000A2C3 A1[646A0100]        <1> 	mov	eax, [csftdf_sf_cluster]
  5795 0000A2C8 E837210000          <1> 	call	get_next_cluster
  5796 0000A2CD 5B                  <1> 	pop	ebx ; *
  5797 0000A2CE 7301                <1> 	jnc	short mcfg_read_fat_file_secs_2
  5798                              <1> 
  5799                              <1> 	;mov	eax, 17; Read error !
  5800 0000A2D0 C3                  <1> 	retn
  5801                              <1> 
  5802                              <1> mcfg_read_fat_file_secs_2:
  5803 0000A2D1 29D2                <1> 	sub	edx, edx ; 0
  5804 0000A2D3 A3[646A0100]        <1> 	mov	[csftdf_sf_cluster], eax ; next cluster
  5805                              <1> 
  5806                              <1> mcfg_read_fat_file_secs_3:
  5807 0000A2D8 C3                  <1> 	retn
  5808                              <1> 
  5809                              <1> mcfg_read_fs_file_sectors:
  5810 0000A2D9 C3                  <1> 	retn
  5811                              <1> 
  5812                              <1> loc_mcfg_load_fs_file:
  5813 0000A2DA C3                  <1> 	retn
  5814                              <1> 
  5815                              <1> load_and_execute_file:
  5816                              <1> 	; 04/01/2017
  5817                              <1> 	; 06/05/2016, 07/05/2016, 11/05/2016
  5818                              <1> 	; 23/04/2016, 24/04/2016
  5819                              <1> 	; 22/04/2016 (TRDOS 386 = TRDOS v2.0)
  5820                              <1> 	; 05/11/2011 
  5821                              <1> 	; (TRDOS v1, CMDINTR.ASM, 'cmp_cmd_run', 'cmp_cmd_external')
  5822                              <1> 	; ('loc_run_check_filename')
  5823                              <1> 	; 29/08/2011
  5824                              <1> 	; 10/09/2011
  5825                              <1> 	; INPUT->
  5826                              <1> 	;	ESI = Path Name address (CommandBuffer address)
  5827                              <1> 	; OUTPUT ->
  5828                              <1> 	;	none (error message will be shown if an error will occur)
  5829                              <1> 	;
  5830                              <1> 	; (EAX, EBX, ECX, EDX, ESI, EDI, EBP will be changed) 
  5831                              <1> 	;
  5832                              <1> loc_run_check_filename:
  5833 0000A2DB 803E20              <1> 	cmp	byte [esi], 20h
  5834 0000A2DE 0F822BE3FFFF        <1> 	jb	loc_cmd_failed
  5835 0000A2E4 7703                <1> 	ja	short loc_run_check_filename_ok
  5836 0000A2E6 46                  <1> 	inc	esi
  5837 0000A2E7 EBF2                <1> 	jmp	short loc_run_check_filename
  5838                              <1> 
  5839                              <1> loc_run_check_filename_ok:
  5840 0000A2E9 C605[A75F0100]00    <1> 	mov	byte [CmdArgStart], 0 ; reset
  5841 0000A2F0 56                  <1> 	push	esi ; *
  5842                              <1> loc_run_get_first_arg_pos:
  5843 0000A2F1 46                  <1> 	inc	esi
  5844 0000A2F2 8A06                <1> 	mov	al, [esi]
  5845 0000A2F4 3C20                <1> 	cmp	al, 20h
  5846 0000A2F6 77F9                <1> 	ja	short loc_run_get_first_arg_pos
  5847 0000A2F8 C60600              <1> 	mov	byte [esi], 0
  5848                              <1> loc_run_get_external_arg_pos:
  5849                              <1> 	; 11/05/2016
  5850 0000A2FB 46                  <1> 	inc	esi
  5851 0000A2FC 8A06                <1> 	mov	al, [esi]
  5852 0000A2FE 3C20                <1> 	cmp	al, 20h
  5853 0000A300 760C                <1> 	jna	short loc_run_parse_path_name
  5854 0000A302 89F0                <1> 	mov	eax, esi
  5855 0000A304 2D[F65F0100]        <1> 	sub	eax, CommandBuffer
  5856 0000A309 A2[A75F0100]        <1> 	mov	byte [CmdArgStart], al
  5857                              <1> loc_run_parse_path_name:
  5858 0000A30E 5E                  <1> 	pop	esi ; *
  5859 0000A30F BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  5860 0000A314 E8D7090000          <1> 	call	parse_path_name
  5861 0000A319 0F82F0E2FFFF        <1> 	jc	loc_cmd_failed
  5862                              <1> 
  5863                              <1> loc_run_check_filename_exists:
  5864 0000A31F BE[28680100]        <1> 	mov	esi, FindFile_Name
  5865 0000A324 803E20              <1> 	cmp	byte [esi], 20h
  5866 0000A327 0F86E2E2FFFF        <1> 	jna	loc_cmd_failed
  5867                              <1> 
  5868                              <1> loc_run_check_exe_filename_ext:
  5869 0000A32D E890020000          <1> 	call	check_prg_filename_ext
  5870 0000A332 0F82D7E2FFFF        <1> 	jc	loc_cmd_failed
  5871                              <1> 	
  5872                              <1> loc_run_check_exe_filename_ext_ok:
  5873 0000A338 66A3[FE6A0100]      <1> 	mov	word [EXE_ID], ax
  5874                              <1> 
  5875                              <1> loc_run_drv:
  5876 0000A33E C605[FD6A0100]00    <1> 	mov	byte [Run_Manual_Path], 0
  5877 0000A345 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
  5878 0000A34A A3[F86A0100]        <1>         mov     [Run_CDirFC], eax
  5879                              <1> 	;
  5880 0000A34F 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  5881 0000A355 8835[A2660100]      <1> 	mov	[RUN_CDRV], dh
  5882                              <1> 
  5883 0000A35B 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  5884 0000A361 38F2                <1> 	cmp	dl, dh
  5885 0000A363 7412                <1> 	je	short loc_run_change_directory
  5886                              <1>                
  5887 0000A365 8005[FD6A0100]02    <1> 	add	byte [Run_Manual_Path], 2
  5888                              <1> 
  5889 0000A36C E80BD4FFFF          <1> 	call	change_current_drive
  5890 0000A371 0F82C3E2FFFF        <1> 	jc	loc_run_cmd_failed
  5891                              <1> 
  5892                              <1> loc_run_change_directory:
  5893 0000A377 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  5894 0000A37E 7623                <1> 	jna	short loc_run_find_executable_file
  5895                              <1> 
  5896 0000A380 FE05[FD6A0100]      <1> 	inc	byte [Run_Manual_Path]
  5897                              <1>      
  5898 0000A386 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  5899                              <1> 
  5900 0000A38C BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  5901 0000A391 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  5902 0000A393 E842030000          <1> 	call	change_current_directory
  5903 0000A398 0F829CE2FFFF        <1> 	jc	loc_run_cmd_failed
  5904                              <1> 
  5905                              <1> loc_run_change_prompt_dir_string:
  5906 0000A39E E857020000          <1> 	call	change_prompt_dir_string
  5907                              <1> 
  5908                              <1> loc_run_find_executable_file:
  5909 0000A3A3 66C705[FC6A0100]00- <1> 	mov	word [Run_Auto_Path], 0
  5909 0000A3AB 00                  <1>
  5910                              <1> 
  5911                              <1> loc_run_find_executable_file_next:
  5912 0000A3AC BE[28680100]        <1> 	mov	esi, FindFile_Name
  5913                              <1> loc_run_find_program_file_next:
  5914 0000A3B1 66B80018            <1> 	mov	ax, 1800h ; Except volume label and dirs
  5915 0000A3B5 E865E7FFFF          <1> 	call	find_first_file
  5916                              <1> 	; ESI = Directory Entry (FindFile_DirEntry) Location
  5917                              <1> 	; EDI = Directory Buffer Directory Entry Location
  5918                              <1> 	; EAX = File size
  5919 0000A3BA 0F835C010000        <1> 	jnc	loc_load_and_run_file
  5920                              <1> 	 
  5921 0000A3C0 3C02                <1> 	cmp	al, 2 ; file not found
  5922 0000A3C2 0F8572E2FFFF        <1> 	jne	loc_run_cmd_failed
  5923                              <1> 
  5924 0000A3C8 66A1[FE6A0100]      <1> 	mov	ax, word [EXE_ID]
  5925 0000A3CE 80FC2E              <1> 	cmp	ah, '.' ; File name has extension sign
  5926 0000A3D1 7424                <1> 	je	short loc_run_check_auto_path
  5927                              <1> 
  5928 0000A3D3 08C0                <1> 	or	al, al
  5929 0000A3D5 7520                <1> 	jnz	short loc_run_check_auto_path
  5930                              <1> 
  5931 0000A3D7 80FC08              <1> 	cmp	ah, 8 ; count of file name chars
  5932 0000A3DA 771B                <1> 	ja	short loc_run_check_auto_path
  5933                              <1> 
  5934                              <1> loc_run_change_file_ext_to_prg:
  5935 0000A3DC 0FB6DC              <1> 	movzx	ebx, ah ; count of file name chars
  5936 0000A3DF BE[28680100]        <1> 	mov	esi, FindFile_Name
  5937 0000A3E4 01F3                <1> 	add	ebx, esi	
  5938                              <1> 	; 07/05/2016
  5939 0000A3E6 C7032E505247        <1> 	mov	dword [ebx],  '.PRG'
  5940 0000A3EC 66C705[FE6A0100]50- <1> 	mov	word [EXE_ID], 'P.'
  5940 0000A3F4 2E                  <1>
  5941 0000A3F5 EBBA                <1> 	jmp	short loc_run_find_program_file_next	
  5942                              <1> 
  5943                              <1> loc_run_check_auto_path:
  5944                              <1> 	; NOTE: /// 07/05/2016 ///
  5945                              <1> 	; If the path is given, value of byte [Run_Manual_Path]
  5946                              <1> 	; will not be ZERO. If so, file searching by using
  5947                              <1> 	; Automatic Path (via 'PATH' environment variable)
  5948                              <1> 	; will not be applicable, because the program file 
  5949                              <1> 	; is already/absolutely not found.
  5950                              <1> 
  5951 0000A3F7 A0[FD6A0100]        <1> 	mov	al, [Run_Manual_Path]
  5952 0000A3FC 08C0                <1> 	or	al, al
  5953 0000A3FE 0F850BE2FFFF        <1> 	jnz	loc_cmd_failed
  5954                              <1> 
  5955                              <1> loc_run_check_auto_path_again:
  5956 0000A404 66833D[FC6A0100]FF  <1> 	cmp	word [Run_Auto_Path], 0FFFFh		 
  5957                              <1> 		; 0FFFFh = Not a valid run path (in ENV block) 
  5958 0000A40C 0F83FDE1FFFF        <1> 	jnb	loc_cmd_failed
  5959                              <1> 	; xor	al, al 
  5960 0000A412 BE[93130100]        <1> 	mov	esi, Cmd_Path ; 'PATH'
  5961 0000A417 BF[46600100]        <1> 	mov	edi, TextBuffer
  5962 0000A41C E848F9FFFF          <1> 	call	get_environment_string
  5963 0000A421 730E                <1> 	jnc	short loc_run_chk_filename_ext_again
  5964 0000A423 66C705[FC6A0100]FF- <1> 	mov	word [Run_Auto_Path], 0FFFFh ; invalid
  5964 0000A42B FF                  <1>
  5965 0000A42C E9DEE1FFFF          <1> 	jmp	loc_cmd_failed
  5966                              <1> 
  5967                              <1> loc_run_chk_filename_ext_again:
  5968 0000A431 89C1                <1> 	mov	ecx, eax ; string length (with zero tail)
  5969 0000A433 49                  <1> 	dec	ecx ; without zero tail
  5970 0000A434 66A1[FE6A0100]      <1> 	mov	ax, [EXE_ID]
  5971 0000A43A 80FC2E              <1> 	cmp	ah, '.'
  5972 0000A43D 740E                <1> 	je	short loc_run_chk_auto_path_pos
  5973                              <1> 	 
  5974                              <1> loc_run_change_file_ext_to_noext_again:
  5975 0000A43F 0FB6DC              <1> 	movzx	ebx, ah
  5976 0000A442 BE[28680100]        <1> 	mov	esi, FindFile_Name
  5977 0000A447 01F3                <1> 	add 	ebx, esi
  5978 0000A449 29C0                <1> 	sub	eax, eax
  5979 0000A44B 8903                <1> 	mov	[ebx], eax ; 0 ; erase extension (.PRG)
  5980                              <1> 
  5981                              <1> loc_run_chk_auto_path_pos:
  5982                              <1> 	;movzx	eax,  word [Run_Auto_Path]
  5983 0000A44D 66A1[FC6A0100]      <1> 	mov	ax, [Run_Auto_Path]
  5984 0000A453 39C8                <1> 	cmp	eax, ecx ; ecx = string length (except zero tail)
  5985 0000A455 0F83B4E1FFFF        <1> 	jnb	loc_cmd_failed
  5986                              <1> 	;or	eax, eax
  5987 0000A45B 6609C0              <1> 	or	ax, ax
  5988 0000A45E 7502                <1> 	jnz	short loc_run_auto_path_pos_move
  5989 0000A460 B005                <1> 	mov	al, 5
  5990                              <1> 
  5991                              <1> loc_run_auto_path_pos_move:
  5992 0000A462 89FE                <1> 	mov	esi, edi ; offset TextBuffer
  5993 0000A464 01C6                <1> 	add	esi, eax
  5994                              <1> 
  5995                              <1> loc_run_auto_path_pos_space_loop:
  5996 0000A466 AC                  <1> 	lodsb
  5997 0000A467 3C20                <1> 	cmp	al, 20h 
  5998 0000A469 74FB                <1> 	je	short loc_run_auto_path_pos_space_loop
  5999 0000A46B 0F829EE1FFFF        <1> 	jb	loc_cmd_failed 
  6000 0000A471 AA                  <1> 	stosb
  6001                              <1> loc_run_auto_path_pos_move_next: 
  6002 0000A472 AC                  <1> 	lodsb
  6003 0000A473 3C3B                <1> 	cmp	al, ';'
  6004 0000A475 7414                <1> 	je	short loc_run_auto_path_pos_move_last_byte
  6005 0000A477 3C20                <1> 	cmp	al, 20h
  6006 0000A479 74F7                <1> 	je	short loc_run_auto_path_pos_move_next
  6007 0000A47B 7203                <1> 	jb	short loc_byte_ptr_end_of_path
  6008 0000A47D AA                  <1> 	stosb
  6009 0000A47E EBF2                <1> 	jmp	short loc_run_auto_path_pos_move_next 
  6010                              <1> 
  6011                              <1> loc_byte_ptr_end_of_path: 
  6012 0000A480 66C705[FC6A0100]FF- <1> 	mov	word [Run_Auto_Path], 0FFFFh ; end of path
  6012 0000A488 FF                  <1>
  6013 0000A489 EB0D                <1> 	jmp	short loc_run_auto_path_move_ok 
  6014                              <1> 
  6015                              <1> loc_run_auto_path_pos_move_last_byte:
  6016 0000A48B 89F0                <1> 	mov	eax, esi
  6017 0000A48D 2D[46600100]        <1> 	sub	eax, TextBuffer 
  6018 0000A492 66A3[FC6A0100]      <1> 	mov	[Run_Auto_Path], ax ; next path position
  6019                              <1> 
  6020                              <1> loc_run_auto_path_move_ok:
  6021 0000A498 4F                  <1> 	dec	edi
  6022 0000A499 B02F                <1> 	mov	al, '/'
  6023 0000A49B 3807                <1> 	cmp	[edi], al
  6024 0000A49D 7403                <1> 	je	short loc_run_auto_path_move_file_name
  6025 0000A49F 47                  <1> 	inc	edi
  6026 0000A4A0 8807                <1> 	mov	[edi], al
  6027                              <1> 
  6028                              <1> loc_run_auto_path_move_file_name:
  6029 0000A4A2 47                  <1> 	inc	edi   
  6030 0000A4A3 BE[28680100]        <1> 	mov	esi, FindFile_Name
  6031                              <1> 
  6032                              <1> loc_run_auto_path_move_fn_loop:
  6033 0000A4A8 AC                  <1> 	lodsb
  6034 0000A4A9 AA                  <1> 	stosb
  6035 0000A4AA 08C0                <1> 	or	al, al
  6036 0000A4AC 75FA                <1> 	jnz	short loc_run_auto_path_move_fn_loop
  6037                              <1> 
  6038 0000A4AE BE[46600100]        <1> 	mov	esi, TextBuffer
  6039 0000A4B3 BF[E6670100]        <1> 	mov	edi, FindFile_Drv
  6040 0000A4B8 E833080000          <1> 	call	parse_path_name
  6041 0000A4BD 0F824CE1FFFF        <1> 	jc	loc_cmd_failed
  6042                              <1> 
  6043 0000A4C3 8A35[465F0100]      <1> 	mov	dh, [Current_Drv]
  6044 0000A4C9 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  6045 0000A4CF 38F2                <1> 	cmp	dl, dh
  6046 0000A4D1 740B                <1> 	je	short loc_run_change_directory_again
  6047                              <1>                
  6048 0000A4D3 E8A4D2FFFF          <1> 	call	change_current_drive
  6049 0000A4D8 0F825CE1FFFF        <1> 	jc	loc_run_cmd_failed
  6050                              <1> 
  6051                              <1> loc_run_change_directory_again:
  6052 0000A4DE 803D[E7670100]20    <1> 	cmp	byte [FindFile_Directory], 20h
  6053 0000A4E5 761D                <1> 	jna	short loc_load_executable_cdir_chk_again
  6054                              <1> 
  6055 0000A4E7 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  6056 0000A4ED BE[E7670100]        <1> 	mov	esi, FindFile_Directory
  6057 0000A4F2 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  6058 0000A4F4 E8E1010000          <1> 	call	change_current_directory
  6059 0000A4F9 0F823BE1FFFF        <1> 	jc	loc_run_cmd_failed
  6060                              <1> 
  6061                              <1> loc_run_chg_prompt_dir_str_again:
  6062 0000A4FF E8F6000000          <1> 	call	change_prompt_dir_string
  6063                              <1> 
  6064                              <1> loc_load_executable_cdir_chk_again:
  6065 0000A504 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
  6066 0000A509 3B05[F86A0100]      <1> 	cmp	eax, [Run_CDirFC]
  6067 0000A50F 0F8597FEFFFF        <1> 	jne	loc_run_find_executable_file_next
  6068 0000A515 30C0                <1> 	xor	al, al ; 0
  6069 0000A517 E9E8FEFFFF          <1> 	jmp	loc_run_check_auto_path_again
  6070                              <1> 
  6071                              <1> loc_load_and_run_file:
  6072                              <1> 	; 13/11/2017
  6073                              <1> 	; 04/01/2017
  6074                              <1> 	; 23/04/2016
  6075 0000A51C BE[28680100]        <1> 	mov	esi, FindFile_Name
  6076 0000A521 BF[46600100]        <1> 	mov	edi, TextBuffer
  6077                              <1> 
  6078                              <1>  	; 24/04/2016
  6079 0000A526 31D2                <1> 	xor	edx, edx
  6080 0000A528 668915[4A040300]    <1> 	mov	word [argc], dx ; 0
  6081 0000A52F 8915[8C030300]      <1> 	mov	dword [u.nread], edx ; 0
  6082                              <1> 
  6083                              <1> loc_load_and_run_file_1:
  6084 0000A535 AC                  <1> 	lodsb	
  6085 0000A536 AA                  <1> 	stosb
  6086 0000A537 FF05[8C030300]      <1> 	inc	dword [u.nread]
  6087 0000A53D 20C0                <1> 	and	al, al
  6088 0000A53F 75F4                <1> 	jnz 	short loc_load_and_run_file_1
  6089                              <1> 	
  6090 0000A541 A0[A75F0100]        <1> 	mov	al, [CmdArgStart]
  6091 0000A546 20C0                <1> 	and	al, al
  6092 0000A548 7445                <1> 	jz	short loc_load_and_run_file_7
  6093                              <1> 
  6094 0000A54A 0FB6F0              <1> 	movzx	esi, al ; 11/05/2016
  6095 0000A54D B950000000          <1> 	mov	ecx, 80
  6096 0000A552 29F1                <1> 	sub	ecx, esi
  6097 0000A554 81C6[F65F0100]      <1> 	add	esi, CommandBuffer
  6098                              <1> 
  6099 0000A55A 66FF05[4A040300]    <1> 	inc	word [argc] ; 11/05/2016
  6100                              <1> 
  6101                              <1> loc_load_and_run_file_2:
  6102 0000A561 AC                  <1> 	lodsb
  6103 0000A562 3C20                <1> 	cmp	al, 20h
  6104 0000A564 7717                <1> 	ja	short loc_load_and_run_file_5	
  6105 0000A566 721E                <1> 	jb	short loc_load_and_run_file_6
  6106                              <1> 
  6107                              <1> loc_load_and_run_file_3:
  6108 0000A568 803E20              <1> 	cmp	byte [esi], 20h
  6109 0000A56B 7707                <1> 	ja	short loc_load_and_run_file_4
  6110 0000A56D 7217                <1> 	jb	short loc_load_and_run_file_6
  6111 0000A56F 46                  <1> 	inc	esi
  6112 0000A570 E2F6                <1> 	loop	loc_load_and_run_file_3
  6113 0000A572 EB12                <1> 	jmp	short loc_load_and_run_file_6
  6114                              <1> 
  6115                              <1> loc_load_and_run_file_4:
  6116 0000A574 28C0                <1> 	sub	al, al ; 0
  6117 0000A576 66FF05[4A040300]    <1> 	inc	word [argc]
  6118                              <1> loc_load_and_run_file_5:
  6119 0000A57D AA                  <1> 	stosb
  6120 0000A57E FF05[8C030300]      <1> 	inc	dword [u.nread]
  6121 0000A584 E2DB                <1> 	loop	loc_load_and_run_file_2
  6122                              <1> 			
  6123                              <1> loc_load_and_run_file_6:
  6124 0000A586 30C0                <1> 	xor	al, al ; 0
  6125 0000A588 AA                  <1> 	stosb
  6126 0000A589 FF05[8C030300]      <1> 	inc	dword [u.nread]
  6127                              <1> loc_load_and_run_file_7:
  6128 0000A58F 8807                <1> 	mov 	[edi], al ; 0
  6129 0000A591 66FF05[4A040300]    <1> 	inc	word [argc] ; 24/04/2016
  6130 0000A598 FF05[8C030300]      <1> 	inc	dword [u.nread] ; 24/04/2016
  6131 0000A59E BE[46600100]        <1> 	mov	esi, TextBuffer
  6132 0000A5A3 8B15[54680100]      <1> 	mov	edx, [FindFile_DirEntry+DirEntry_FileSize]
  6133 0000A5A9 66A1[4C680100]      <1> 	mov	ax, [FindFile_DirEntry+DirEntry_FstClusHI]
  6134 0000A5AF C1E010              <1> 	shl	eax, 16 ; 13/11/2017
  6135 0000A5B2 66A1[52680100]      <1> 	mov	ax, [FindFile_DirEntry+DirEntry_FstClusLO]
  6136                              <1> 	; EAX = First Cluster number
  6137                              <1> 	; EDX = File Size
  6138                              <1> 	; ESI = Argument list address
  6139                              <1> 	; [argc] = argument count
  6140                              <1> 	; [u.nread] = argument list length
  6141 0000A5B8 E8CA3F0000          <1> 	call	load_and_run_file ; trdosk6.s
  6142                              <1>         ;jc	loc_run_cmd_failed ; 04/01/2017
  6143                              <1> loc_load_and_run_file_8: ; 06/05/2016
  6144 0000A5BD E98BE9FFFF          <1> 	jmp	loc_file_rw_restore_retn
  6145                              <1> 
  6146                              <1> check_prg_filename_ext:
  6147                              <1> 	; 23/04/2016 (TRDOS 386 = TRDOS v2.0)
  6148                              <1> 	; 10/09/2011 
  6149                              <1> 	; (TRDOS v1, CMDINTR.ASM, 'proc_check_exe_filename_ext')
  6150                              <1> 	; 14/11/2009
  6151                              <1> 	; INPUT -> 
  6152                              <1> 	;	ESI = Dot File Name
  6153                              <1> 	; OUTPUT ->
  6154                              <1> 	;     cf = 0 -> EXE_ID in AL
  6155                              <1> 	;	ESI = Last char + 1 position
  6156                              <1> 	;     cf = 1 -> Invalid executable file name
  6157                              <1> 	;	or no file name extension if AH<=8
  6158                              <1> 	;	AL = Last file name char     
  6159                              <1> 	;     cf = 0 -> AL='P' (PRG), AL=0 (no extension)
  6160                              <1> 	;
  6161                              <1> 	; (Modified registers: EAX, ESI)
  6162                              <1>   
  6163 0000A5C2 30E4                <1> 	xor	ah, ah
  6164                              <1> loc_run_check_filename_ext:	
  6165 0000A5C4 AC                  <1> 	lodsb
  6166 0000A5C5 3C21                <1> 	cmp	al, 21h
  6167 0000A5C7 7229                <1> 	jb	short loc_check_exe_fn_retn 
  6168 0000A5C9 FEC4                <1> 	inc	ah
  6169 0000A5CB 3C2E                <1> 	cmp	al, '.'
  6170 0000A5CD 75F5                <1> 	jne	short loc_run_check_filename_ext	
  6171                              <1> 		 
  6172                              <1> loc_run_check_filename_ext_dot:
  6173 0000A5CF 80FC02              <1> 	cmp	ah, 2 ; .??? is not valid
  6174 0000A5D2 88C4                <1> 	mov	ah, al ; '.' 
  6175 0000A5D4 7219                <1> 	jb	short loc_check_prg_fn_retn
  6176                              <1> 
  6177                              <1> loc_run_check_filename_ext_dot_ok:
  6178 0000A5D6 AC                  <1> 	lodsb
  6179 0000A5D7 24DF                <1> 	and	al, 0DFh 
  6180                              <1> 
  6181                              <1> loc_run_check_filename_ext_prg:
  6182 0000A5D9 3C50                <1> 	cmp	al, 'P'
  6183 0000A5DB 7212                <1> 	jb	short loc_check_prg_fn_retn
  6184 0000A5DD 7711                <1> 	ja	short loc_check_prg_fn_stc
  6185 0000A5DF AC                  <1> 	lodsb
  6186 0000A5E0 24DF                <1> 	and	al, 0DFh 
  6187 0000A5E2 3C52                <1> 	cmp	al, 'R'
  6188 0000A5E4 750A                <1> 	jne	short loc_check_prg_fn_stc
  6189 0000A5E6 AC                  <1> 	lodsb
  6190 0000A5E7 24DF                <1> 	and	al, 0DFh
  6191 0000A5E9 3C47                <1> 	cmp	al, 'G'
  6192 0000A5EB 7503                <1> 	jne	short loc_check_prg_fn_stc
  6193                              <1> 
  6194 0000A5ED B050                <1> 	mov	al, 'P'
  6195                              <1> loc_check_prg_fn_retn:
  6196 0000A5EF C3                  <1> 	retn
  6197                              <1> 
  6198                              <1> loc_check_prg_fn_stc:
  6199 0000A5F0 F9                  <1> 	stc
  6200 0000A5F1 C3                  <1> 	retn
  6201                              <1>  
  6202                              <1> loc_check_exe_fn_retn:
  6203 0000A5F2 28C0                <1> 	sub	al, al ; 0
  6204 0000A5F4 C3                  <1> 	retn
  6205                              <1>               
  6206                              <1> find_and_list_files:
  6207 0000A5F5 C3                  <1> 	retn
  6208                              <1> set_exec_arguments:
  6209 0000A5F6 C3                  <1> 	retn
  6210                              <1> delete_fs_directory:
  6211 0000A5F7 31C0                <1> 	xor eax, eax
  6212 0000A5F9 C3                  <1> 	retn
  2864                                  %include 'trdosk4.s' ; 24/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - Directory Functions : trdosk4.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 29/12/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; DIR.ASM (09/10/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> 
    14                              <1> ; DIR.ASM  [ TRDOS KERNEL - COMMAND EXECUTER SECTION - DIRECTORY FUNCTIONS ]
    15                              <1> ; (c) 2004-2010  Erdogan TAN  [ 17/01/2004 ]  Last Update: 09/10/2011
    16                              <1> ; FILE.ASM [ FILE FUNCTIONS ] Last Update: 09/10/2011
    17                              <1> 
    18                              <1> change_prompt_dir_string:
    19                              <1> 	; 05/10/2016
    20                              <1> 	; 24/01/2016 (TRDOS 386 = TRDOS v2.0)
    21                              <1> 	; 27/03/2011
    22                              <1> 	; 09/10/2009
    23                              <1> 	; INPUT/OUTPUT => none
    24                              <1> 	; this procedure changes current directory string/text  
    25                              <1> 	; 2005
    26                              <1> 
    27 0000A5FA BE[A3660100]        <1> 	mov	esi, PATH_Array
    28                              <1> change_prompt_dir_str: ; 05/10/2016 (call from 'set_working_path')
    29 0000A5FF BF[4A5F0100]        <1> 	mov	edi, Current_Directory
    30 0000A604 8A25[445F0100]      <1> 	mov	ah, [Current_Dir_Level]
    31 0000A60A E807000000          <1> 	call	set_current_directory_string
    32 0000A60F 880D[A55F0100]      <1> 	mov	[Current_Dir_StrLen], cl
    33                              <1> 
    34 0000A615 C3                  <1> 	retn
    35                              <1> 
    36                              <1> set_current_directory_string:
    37                              <1> 	; 24/01/2016 (TRDOS 386 = TRDOS v2.0)
    38                              <1> 	; 27/03/2011
    39                              <1> 	; 09/10/2009
    40                              <1> 	; INPUT:
    41                              <1> 	;    ESI = Path Array Address 
    42                              <1> 	;    EDI = Current Directory String Buffer
    43                              <1> 	;    AH = Current Directory Level
    44                              <1> 	; OUTPUT => EAX, EBX, ESI will be changed
    45                              <1> 	;    EDI will be same with input
    46                              <1> 	;    ECX = Current Directory String Length 
    47                              <1> 
    48 0000A616 57                  <1> 	push    edi
    49 0000A617 80FC00              <1> 	cmp     ah, 0
    50 0000A61A 7652                <1> 	jna	short pass_write_path
    51 0000A61C 83C610              <1> 	add	esi, 16
    52 0000A61F 89F3                <1> 	mov	ebx, esi
    53                              <1> loc_write_path:
    54 0000A621 B908000000          <1> 	mov	ecx, 8
    55                              <1> path_write_dirname1:
    56 0000A626 AC                  <1> 	lodsb
    57 0000A627 3C20                <1> 	cmp	al, 20h
    58 0000A629 7612                <1> 	jna	short pass_write_dirname1
    59 0000A62B AA                  <1> 	stosb
    60 0000A62C 81FF[A45F0100]      <1> 	cmp	edi, End_Of_Current_Dir_Str
    61 0000A632 733A                <1> 	jnb	short pass_write_path
    62 0000A634 E2F0                <1> 	loop	path_write_dirname1
    63 0000A636 803E20              <1> 	cmp	byte [esi], 20h
    64 0000A639 7624                <1> 	jna	short pass_write_dirname2
    65 0000A63B EB0A                <1> 	jmp     short loc_put_dot_cont_ext
    66                              <1> pass_write_dirname1:
    67 0000A63D 89DE                <1> 	mov	esi, ebx
    68 0000A63F 83C608              <1> 	add	esi, 8
    69 0000A642 803E20              <1> 	cmp	byte [esi], 20h
    70 0000A645 7618                <1> 	jna	short pass_write_dirname2
    71                              <1> loc_put_dot_cont_ext:
    72 0000A647 C6072E              <1> 	mov	byte [edi], "."
    73                              <1> 	;mov	ecx, 3
    74 0000A64A B103                <1> 	mov	cl, 3
    75                              <1> loc_check_dir_name_ext:
    76 0000A64C AC                  <1> 	lodsb
    77 0000A64D 47                  <1> 	inc	edi
    78 0000A64E 3C20                <1> 	cmp	al, 20h
    79 0000A650 760D                <1> 	jna	short pass_write_dirname2
    80 0000A652 8807                <1> 	mov	[edi], al
    81 0000A654 81FF[A45F0100]      <1> 	cmp	edi, End_Of_Current_Dir_Str
    82 0000A65A 7312                <1> 	jnb	short pass_write_path
    83 0000A65C E2EE                <1> 	loop    loc_check_dir_name_ext
    84 0000A65E 47                  <1> 	inc	edi
    85                              <1> pass_write_dirname2:
    86 0000A65F FECC                <1> 	dec	ah
    87 0000A661 740B                <1> 	jz      short pass_write_path
    88 0000A663 83C310              <1> 	add	ebx, 16
    89 0000A666 89DE                <1> 	mov	esi, ebx
    90 0000A668 C6072F              <1> 	mov	byte [edi],"/"
    91 0000A66B 47                  <1> 	inc	edi
    92 0000A66C EBB3                <1> 	jmp	short loc_write_path
    93                              <1> pass_write_path:
    94 0000A66E C60700              <1> 	mov	byte [edi], 0
    95 0000A671 47                  <1> 	inc	edi
    96 0000A672 89F9                <1> 	mov	ecx, edi
    97 0000A674 5F                  <1> 	pop	edi
    98 0000A675 29F9                <1> 	sub	ecx, edi
    99                              <1> 	; ECX = Current Directory String Length
   100 0000A677 C3                  <1> 	retn
   101                              <1> 
   102                              <1> get_current_directory:
   103                              <1> 	; 15/10/2016
   104                              <1> 	; 14/02/2016
   105                              <1> 	; 24/01/2016 (TRDOS 386 = TRDOS v2.0)
   106                              <1> 	; 27/03/2011
   107                              <1> 	;
   108                              <1> 	; INPUT-> ESI = Current Directory Buffer
   109                              <1> 	;         DL = TRDOS Logical Dos Drive Number + 1
   110                              <1> 	;              (0= Default/Current Drive)
   111                              <1> 	;           
   112                              <1> 	;   Note: Required dir buffer length may be <= 92 bytes
   113                              <1> 	;         for TRDOS (7*12 name chars + 7 slash + 0)
   114                              <1> 	; OUTPUT ->  ESI = Current Directory Buffer
   115                              <1> 	;            EAX, EBX, ECX, EDX, EDI will be changed
   116                              <1> 	;            CX/CL = Current Directory String Length
   117                              <1> 	;	     DL = Drive Number (0 based)
   118                              <1> 	;            (If input is 0, output is current drv number) 
   119                              <1> 	;            DH = same with input 
   120                              <1> 	;   cf = 0 -> AL = 0
   121                              <1> 	;   cf = 1 -> error code in AL 
   122                              <1>               
   123                              <1> loc_get_current_drive_0:
   124 0000A678 80FA00              <1> 	cmp	dl, 0
   125 0000A67B 7708                <1> 	ja	short loc_get_current_drive_1
   126 0000A67D 8A15[465F0100]      <1> 	mov	dl, [Current_Drv]
   127 0000A683 EB17                <1> 	jmp	short loc_get_current_drive_2
   128                              <1> loc_get_current_drive_1:
   129 0000A685 FECA                <1> 	dec 	dl
   130 0000A687 3A15[C6120100]      <1> 	cmp	dl, [Last_DOS_DiskNo]
   131 0000A68D 760D                <1> 	jna	short loc_get_current_drive_2
   132 0000A68F B80F000000          <1> 	mov	eax, 0Fh ; Invalid drive (Drive not ready!)
   133 0000A694 F5                  <1> 	cmc 	; stc
   134 0000A695 C3                  <1> 	retn
   135                              <1> 
   136                              <1> loc_get_current_drive_not_ready_retn:
   137 0000A696 5E                  <1> 	pop	esi
   138                              <1> 	;mov	eax, 15
   139 0000A697 66B80F00            <1> 	mov	ax, 15 ; Drive not ready
   140 0000A69B C3                  <1> 	retn  
   141                              <1>  
   142                              <1> loc_get_current_drive_2:
   143 0000A69C 31C0                <1> 	xor	eax, eax
   144 0000A69E 88D4                <1> 	mov	ah, dl
   145 0000A6A0 56                  <1> 	push	esi
   146 0000A6A1 BE00010900          <1> 	mov	esi, Logical_DOSDisks
   147 0000A6A6 01C6                <1> 	add	esi, eax
   148 0000A6A8 8A06                <1> 	mov	al, [esi+LD_Name] 
   149 0000A6AA 3C41                <1> 	cmp	al, 'A'
   150 0000A6AC 72E8                <1> 	jb	short loc_get_current_drive_not_ready_retn
   151                              <1> 
   152 0000A6AE 8A667F              <1> 	mov	ah, [esi+LD_CDirLevel]
   153 0000A6B1 08E4                <1> 	or	ah, ah
   154 0000A6B3 7506                <1> 	jnz	short loc_get_current_drive_3
   155                              <1> 
   156                              <1> 	;xor	ah, ah ; mov ah, 0
   157 0000A6B5 8826                <1> 	mov	[esi], ah
   158 0000A6B7 31C9                <1> 	xor	ecx, ecx
   159 0000A6B9 EB1C                <1> 	jmp	short loc_get_current_drive_4
   160                              <1> 
   161                              <1> loc_get_current_drive_3:
   162 0000A6BB BF[A3660100]        <1>         mov     edi, PATH_Array
   163 0000A6C0 57                  <1> 	push	edi
   164 0000A6C1 81C680000000        <1> 	add	esi, LD_CurrentDirectory
   165 0000A6C7 B920000000          <1> 	mov	ecx, 32
   166 0000A6CC F3A5                <1> 	rep	movsd
   167 0000A6CE 5E                  <1> 	pop	esi ; Path Array Address
   168 0000A6CF 5F                  <1> 	pop	edi ; pushed esi (current dir buffer offset) 
   169                              <1> 	;
   170 0000A6D0 E841FFFFFF          <1> 	call	set_current_directory_string
   171 0000A6D5 89FE                <1> 	mov	esi, edi
   172                              <1> 
   173                              <1> loc_get_current_drive_4:
   174 0000A6D7 30C0                <1> 	xor	al, al
   175 0000A6D9 C3                  <1> 	retn
   176                              <1> 
   177                              <1> change_current_directory:
   178                              <1> 	; 19/02/2016
   179                              <1> 	; 11/02/2016
   180                              <1> 	; 10/02/2016
   181                              <1> 	; 08/02/2016
   182                              <1> 	; 06/02/2016 (TRDOS 386 = TRDOS v2.0)
   183                              <1> 	; 18/09/2011 (DIR.ASM, 09/10/2011)	
   184                              <1> 	; 04/10/2009
   185                              <1> 	; 2005
   186                              <1> 	; INPUT -> 
   187                              <1> 	;	ESI = Directory string
   188                              <1> 	;	ah = CD command (CDh = save current dir string)
   189                              <1> 	; OUTPUT -> 
   190                              <1> 	; 	EDI = DOS Drive Description Table
   191                              <1> 	; 	cf = 1 -> error
   192                              <1> 	;	   EAX = Error code
   193                              <1> 	;	cf = 0 -> successful
   194                              <1> 	;	   ESI = PATH_Array
   195                              <1> 	;	   EAX = Current Directory First Cluster
   196                              <1> 	;
   197                              <1> 	; (EAX, EBX, ECX, EDX, ESI, EDI will be changed)
   198                              <1> 	
   199 0000A6DA 8825[31670100]      <1> 	mov	[CD_COMMAND], ah
   200 0000A6E0 803E2F              <1> 	cmp	byte [esi], '/'
   201 0000A6E3 7505                <1> 	jne	short loc_ccd_cdir_level
   202 0000A6E5 46                  <1> 	inc	esi
   203 0000A6E6 30C0                <1> 	xor	al, al
   204 0000A6E8 EB05                <1> 	jmp	short loc_ccd_parse_path_name
   205                              <1> loc_ccd_cdir_level:
   206 0000A6EA A0[445F0100]        <1> 	mov	al, [Current_Dir_Level]
   207                              <1> loc_ccd_parse_path_name:
   208 0000A6EF 88C4                <1> 	mov	ah, al
   209 0000A6F1 BF[A3660100]        <1> 	mov	edi, PATH_Array
   210                              <1> 
   211                              <1> ; Reset directory levels > cdir level
   212                              <1> 	; is this required !?
   213                              <1> 	;
   214                              <1> 	; Relations:
   215                              <1> 	; MAINPROG.ASM (pass_ccdrv_reset_cdir_FAT_fcluster)
   216                              <1> 	; proc_parse_dir_name,
   217                              <1> 	; proc_change_current_directory (this procedure)
   218                              <1> 	; proc_change_prompt_dir_string 
   219                              <1>  
   220 0000A6F6 0FB6C8              <1> 	movzx	ecx, al
   221 0000A6F9 FEC1                <1> 	inc	cl
   222 0000A6FB C0E104              <1> 	shl	cl, 4
   223 0000A6FE 01CF                <1> 	add	edi, ecx
   224 0000A700 B107                <1> 	mov	cl, 7
   225 0000A702 28C1                <1> 	sub	cl, al
   226 0000A704 C0E102              <1> 	shl	cl, 2
   227 0000A707 89C3                <1> 	mov	ebx, eax
   228 0000A709 31C0                <1> 	xor	eax, eax ; 0
   229 0000A70B F3AB                <1> 	rep	stosd
   230 0000A70D 89D8                <1> 	mov	eax, ebx
   231                              <1> 
   232 0000A70F BF[A3660100]        <1> 	mov	edi, PATH_Array
   233                              <1> 
   234 0000A714 803E20              <1> 	cmp	byte [esi], 20h
   235 0000A717 F5                  <1> 	cmc
   236 0000A718 7305                <1> 	jnc	short pass_ccd_parse_dir_name
   237                              <1> 
   238                              <1> 		; ESI = Path name
   239                              <1> 		; AL = CCD_Level
   240 0000A71A E872010000          <1>         call    parse_dir_name
   241                              <1> 		; AL = CCD_Level 
   242                              <1> 		; AH = Last_Dir_Level
   243                              <1> 		; (EDI = PATH_Array)
   244                              <1> 
   245                              <1> pass_ccd_parse_dir_name:
   246 0000A71F 9C                  <1> 	pushf
   247                              <1> 
   248                              <1> 	;mov	[CCD_Level], al
   249                              <1>         ;mov	[Last_Dir_Level], ah
   250 0000A720 66A3[27670100]      <1> 	mov	[CCD_Level], ax
   251                              <1> 
   252 0000A726 31DB                <1> 	xor	ebx, ebx
   253 0000A728 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
   254 0000A72E BE00010900          <1> 	mov	esi, Logical_DOSDisks
   255 0000A733 01DE                <1> 	add	esi, ebx
   256                              <1> 
   257 0000A735 9D                  <1> 	popf 
   258 0000A736 720A                <1> 	jc	short loc_ccd_bad_path_name_retn
   259                              <1> 
   260 0000A738 8935[23670100]      <1> 	mov	[CCD_DriveDT], esi
   261                              <1> 
   262 0000A73E 3C07                <1> 	cmp	al, 7
   263 0000A740 7209                <1> 	jb	short loc_ccd_load_child_dir
   264                              <1> 
   265                              <1> loc_ccd_bad_path_name_retn:
   266 0000A742 87F7                <1> 	xchg	esi, edi
   267 0000A744 B813000000          <1> 	mov	eax, 19 ; Bad directory/path name 
   268 0000A749 F9                  <1> 	stc
   269                              <1> loc_ccd_retn_p:
   270 0000A74A C3                  <1> 	retn
   271                              <1> 
   272                              <1> loc_ccd_load_child_dir:
   273                              <1> 	; AL = CCD_Level
   274 0000A74B 08C0                <1> 	or	al, al
   275 0000A74D 7468                <1> 	jz	short loc_ccd_load_root_dir
   276                              <1> 
   277 0000A74F 6689C1              <1> 	mov	cx, ax
   278 0000A752 C0E004              <1> 	shl	al, 4
   279 0000A755 0FB6F0              <1> 	movzx	esi, al
   280 0000A758 01FE                <1>      	add	esi, edi  ; offset PATH_Array
   281                              <1> 
   282 0000A75A 8B460C              <1> 	mov	eax, [esi+12]
   283 0000A75D 38E9                <1> 	cmp	cl, ch
   284 0000A75F 0F84FA000000        <1>         je      loc_ccd_load_sub_directory
   285 0000A765 A3[405F0100]        <1> 	mov	[Current_Dir_FCluster], eax
   286                              <1> 
   287                              <1> loc_ccd_load_child_dir_next:
   288 0000A76A 83C610              <1> 	add	esi, 16 ; DOS DirEntry Format FileName Address
   289                              <1> 
   290                              <1>  	; Directory attribute : 10h
   291 0000A76D B010                <1> 	mov	al, 00010000b ; 10h (Attrib AND mask)
   292                              <1> 	;mov	ah, 11001000b ; C8h
   293                              <1> 	; Volume name attribute: 8h
   294 0000A76F B408                <1> 	mov	ah, 00001000b ; 08h (Attrib NAND, AND --> zero mask)
   295                              <1> 
   296 0000A771 6631C9              <1> 	xor	cx, cx  
   297 0000A774 E8B5010000          <1> 	call	locate_current_dir_file
   298 0000A779 7353                <1> 	jnc	short loc_ccd_set_dir_cluster_ptr
   299                              <1> 
   300                              <1> 	 ; 19/02/2016
   301                              <1> 	;mov	edi, [CCD_DriveDT]
   302 0000A77B 8A25[27670100]      <1> 	mov	ah, [CCD_Level]
   303 0000A781 803D[31670100]CD    <1> 	cmp	byte [CD_COMMAND], 0CDh ;'CD' command or another
   304 0000A788 7509                <1> 	jne	short loc_ccd_load_child_dir_err
   305                              <1> 	; It is better to save recent successful part 
   306                              <1> 	; of the (requested) path as current directory.
   307                              <1> 	; (Otherwise the path would be reset to back
   308                              <1> 	; on the next 'CD' command.)
   309 0000A78A 88E1                <1> 	mov	cl, ah
   310 0000A78C 50                  <1> 	push	eax
   311 0000A78D E8E3000000          <1> 	call	loc_ccd_save_current_dir
   312 0000A792 58                  <1> 	pop	eax
   313                              <1> loc_ccd_load_child_dir_err:            
   314 0000A793 3C03                <1> 	cmp	al, 3	; AL = 2 => File not found error
   315 0000A795 7202                <1> 	jb	short loc_ccd_path_not_found_retn
   316 0000A797 F9                  <1> 	stc
   317 0000A798 C3                  <1> 	retn
   318                              <1> 
   319                              <1> loc_ccd_path_not_found_retn:
   320 0000A799 B003                <1> 	mov	al, 3	; Path not found
   321 0000A79B C3                  <1> 	retn
   322                              <1> 
   323                              <1> loc_ccd_load_FAT_root_dir:
   324 0000A79C 803D[455F0100]02    <1> 	cmp	byte [Current_FATType], 2
   325 0000A7A3 776B                <1> 	ja	short loc_ccd_load_FAT32_root_dir
   326                              <1> 
   327                              <1> 	;mov	esi, [CCD_DriveDT]
   328                              <1> 	;push	esi
   329 0000A7A5 E8B51D0000          <1> 	call	load_FAT_root_directory
   330                              <1> 	;pop	edi ; Dos Drv Description Table
   331                              <1> 
   332 0000A7AA 89F7                <1> 	mov	edi, esi
   333 0000A7AC BE[A3660100]        <1> 	mov	esi, PATH_Array
   334 0000A7B1 7297                <1> 	jc	short loc_ccd_retn_p
   335                              <1> 
   336 0000A7B3 31C0                <1> 	xor	eax, eax
   337 0000A7B5 EB78                <1>         jmp	short loc_ccd_set_cdfc
   338                              <1> 
   339                              <1> loc_ccd_load_root_dir:
   340 0000A7B7 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
   341 0000A7BE 73DC                <1> 	jnb	short loc_ccd_load_FAT_root_dir
   342                              <1> 
   343                              <1> loc_ccd_load_FS_root_dir:
   344 0000A7C0 E8611E0000          <1> 	call	load_FS_root_directory
   345 0000A7C5 EB5C                <1> 	jmp	short pass_ccd_load_FAT_sub_directory
   346                              <1> 
   347                              <1> loc_ccd_load_FS_sub_directory_next:
   348 0000A7C7 E85B1E0000          <1> 	call	load_FS_sub_directory
   349 0000A7CC EB1F                <1> 	jmp	short pass_ccd_set_dir_cluster_ptr  
   350                              <1> 
   351                              <1> loc_ccd_set_dir_cluster_ptr:
   352                              <1> 	; EDI = Directory Entry
   353 0000A7CE 668B4714            <1> 	mov	ax, [edi+20] ; First Cluster High Word
   354 0000A7D2 C1E010              <1> 	shl	eax, 16
   355 0000A7D5 668B471A            <1> 	mov	ax, [edi+26] ; First Cluster Low Word
   356                              <1> 
   357 0000A7D9 8B35[23670100]      <1> 	mov	esi, [CCD_DriveDT]
   358 0000A7DF 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
   359 0000A7E6 72DF                <1> 	jb	short loc_ccd_load_FS_sub_directory_next
   360                              <1> 	;push	esi
   361 0000A7E8 E8FD1D0000          <1> 	call	load_FAT_sub_directory
   362                              <1> 	;pop	edi ; Dos Drv Description Table
   363                              <1> 
   364                              <1> pass_ccd_set_dir_cluster_ptr:
   365                              <1> 	;mov	edi, esi
   366 0000A7ED BE[A3660100]        <1> 	mov	esi, PATH_Array
   367 0000A7F2 7264                <1> 	jc	short loc_ccd_retn_c
   368                              <1> 
   369 0000A7F4 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
   370                              <1> 
   371 0000A7F9 FE05[27670100]      <1> 	inc	byte [CCD_Level]
   372 0000A7FF 0FB61D[27670100]    <1> 	movzx	ebx, byte [CCD_Level]
   373 0000A806 C0E304              <1> 	shl	bl, 4 ; * 16 (<= 128)   
   374 0000A809 01DE                <1> 	add	esi, ebx ; 19/02/2016
   375 0000A80B 89460C              <1> 	mov	[esi+12], eax
   376 0000A80E EB1F                <1> 	jmp	short loc_ccd_set_cdfc
   377                              <1> 
   378                              <1> loc_ccd_load_FAT32_root_dir:
   379 0000A810 BE[A3660100]        <1> 	mov	esi, PATH_Array
   380 0000A815 8B460C              <1> 	mov	eax, [esi+12]
   381 0000A818 8B35[23670100]      <1> 	mov	esi, [CCD_DriveDT]
   382                              <1>  
   383                              <1> loc_ccd_load_FAT_sub_directory:
   384                              <1> 	;push	esi
   385 0000A81E E8C71D0000          <1> 	call	load_FAT_sub_directory
   386                              <1> 	;pop	edi ; Dos Drv Description Table
   387                              <1> 
   388                              <1> pass_ccd_load_FAT_sub_directory:
   389                              <1> 	;mov	edi, esi
   390 0000A823 BE[A3660100]        <1> 	mov	esi, PATH_Array
   391 0000A828 722E                <1> 	jc	short loc_ccd_retn_c
   392                              <1> 
   393 0000A82A A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
   394                              <1> 
   395                              <1> loc_ccd_set_cdfc:
   396 0000A82F 8A0D[27670100]      <1> 	mov	cl, [CCD_Level]
   397 0000A835 880D[445F0100]      <1> 	mov	[Current_Dir_Level], cl
   398 0000A83B A3[405F0100]        <1> 	mov	[Current_Dir_FCluster], eax
   399                              <1> 
   400 0000A840 8A2D[28670100]      <1> 	mov	ch, [Last_Dir_Level]
   401 0000A846 38E9                <1> 	cmp	cl, ch 
   402 0000A848 0F821CFFFFFF        <1> 	jb	loc_ccd_load_child_dir_next
   403                              <1> 	
   404 0000A84E 803D[31670100]CD    <1> 	cmp	byte [CD_COMMAND], 0CDh ;'CD' command or another
   405 0000A855 741E                <1> 	je	short loc_ccd_save_current_dir
   406                              <1> 
   407                              <1>         ; jne -> don't save, restore (the previous cdir) later !
   408                              <1>         ; (saving the cdir would prevent previous cdir restoration!)
   409                              <1> 
   410 0000A857 F8                  <1> 	clc
   411                              <1> 
   412                              <1> loc_ccd_retn_c:
   413 0000A858 8B3D[23670100]      <1> 	mov	edi, [CCD_DriveDT]
   414 0000A85E C3                  <1> 	retn
   415                              <1> 
   416                              <1> loc_ccd_load_sub_directory:
   417 0000A85F 8B35[23670100]      <1> 	mov	esi, [CCD_DriveDT]
   418 0000A865 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
   419 0000A86C 73B0                <1> 	jnb	short loc_ccd_load_FAT_sub_directory 
   420 0000A86E E8B41D0000          <1> 	call	load_FS_sub_directory
   421 0000A873 EBAE                <1> 	jmp	short pass_ccd_load_FAT_sub_directory 
   422                              <1> 
   423                              <1> loc_ccd_save_current_dir:
   424 0000A875 BE[A3660100]        <1> 	mov	esi, PATH_Array ; 19/02/2016
   425 0000A87A 8B3D[23670100]      <1> 	mov	edi, [CCD_DriveDT]
   426 0000A880 57                  <1> 	push	edi
   427 0000A881 83C77F              <1>         add     edi, LD_CDirLevel
   428 0000A884 880F                <1> 	mov	[edi], cl
   429 0000A886 47                  <1> 	inc	edi ; LD_CurrentDirectory 
   430 0000A887 56                  <1> 	push	esi
   431                              <1> 	;mov	ecx, 32  ; always < 65536 (in this procedure)
   432 0000A888 66B92000            <1> 	mov	cx, 32
   433 0000A88C F3A5                <1> 	rep	movsd
   434                              <1> 	; Current directory has been saved to 
   435                              <1> 	; the DOS drive description table, cdir area !
   436 0000A88E 5E                  <1> 	pop	esi  ; PATH_Array
   437 0000A88F 5F                  <1> 	pop	edi  ; Dos Drv Description Table
   438                              <1> 
   439 0000A890 C3                  <1> 	retn
   440                              <1> 
   441                              <1> parse_dir_name:
   442                              <1> 	; 11/02/2016
   443                              <1> 	; 10/02/2016
   444                              <1> 	; 07/02/2016 (TRDOS 386 = TRDOS v2.0)
   445                              <1> 	; 18/09/2011
   446                              <1> 	; 17/10/2009
   447                              <1> 	; INPUT ->
   448                              <1> 	;	ESI = ASCIIZ Directory String Address
   449                              <1> 	;	AL = Current Directory Level
   450                              <1> 	;	EDI = Destination Adress
   451                              <1> 	;	     (8 levels, each one 12+4 byte)
   452                              <1> 	; OUTPUT ->
   453                              <1> 	;	EDI = Dir Entry Formatted Array
   454                              <1> 	;	     with zero cluster pointer at the last level
   455                              <1> 	;	AH = Last Dir Level
   456                              <1> 	;	AL = Current Dir Level
   457                              <1> 	;
   458                              <1> 	; (esi, ebx, ecx will be changed) 
   459                              <1> 
   460                              <1> 	;mov	[PATH_Array_Ptr], edi
   461 0000A891 88C4                <1> 	mov	ah, al
   462 0000A893 66A3[C8670100]      <1> 	mov	[PATH_CDLevel], ax
   463                              <1> repeat_ppdn_check_slash:
   464 0000A899 AC                  <1> 	lodsb
   465 0000A89A 3C2F                <1> 	cmp	al, '/'
   466 0000A89C 74FB                <1> 	je	short repeat_ppdn_check_slash
   467 0000A89E 3C21                <1> 	cmp	al, 21h
   468 0000A8A0 7219                <1> 	jb	short loc_ppdn_retn
   469 0000A8A2 57                  <1> 	push	edi
   470                              <1> loc_ppdn_get_dir_name:
   471 0000A8A3 B90C000000          <1> 	mov	ecx, 12
   472 0000A8A8 BF[CA670100]        <1> 	mov	edi, Dir_File_Name
   473                              <1> repeat_ppdn_get_dir_name:
   474 0000A8AD AA                  <1> 	stosb
   475 0000A8AE AC                  <1> 	lodsb
   476 0000A8AF 3C2F                <1> 	cmp	al, '/'
   477 0000A8B1 740A                <1> 	je	short loc_check_level_dot_conv_dir_name
   478 0000A8B3 3C20                <1> 	cmp	al, 20h
   479 0000A8B5 7605                <1> 	jna	short loc_ppdn_end_of_path_scan
   480 0000A8B7 E2F4                <1> 	loop	repeat_ppdn_get_dir_name
   481 0000A8B9 5F                  <1> 	pop	edi
   482 0000A8BA F9                  <1> 	stc
   483                              <1> loc_ppdn_retn:
   484 0000A8BB C3                  <1> 	retn
   485                              <1> 
   486                              <1> loc_ppdn_end_of_path_scan:
   487 0000A8BC 4E                  <1> 	dec	esi
   488                              <1> loc_check_level_dot_conv_dir_name:
   489 0000A8BD 31C0                <1> 	xor	eax, eax
   490 0000A8BF AA                  <1> 	stosb
   491 0000A8C0 89F3                <1> 	mov	ebx, esi
   492 0000A8C2 BE[CA670100]        <1> 	mov	esi, Dir_File_Name
   493 0000A8C7 AC                  <1> 	lodsb
   494                              <1> repeat_ppdn_name_check_dot:
   495 0000A8C8 3C2E                <1> 	cmp	al, '.'
   496 0000A8CA 7509                <1> 	jne	short loc_ppdn_convert_sub_dir_name
   497                              <1> repeat_ppdn_name_dot_dot:
   498 0000A8CC AC                  <1> 	lodsb
   499 0000A8CD 3C2E                <1> 	cmp	al, '.'
   500 0000A8CF 743E                <1> 	je	short loc_ppdn_dot_dot
   501 0000A8D1 3C21                <1> 	cmp	al, 21h
   502 0000A8D3 7226                <1> 	jb	short pass_ppdn_convert_sub_dir_name
   503                              <1> loc_ppdn_convert_sub_dir_name:
   504 0000A8D5 8A25[C9670100]      <1> 	mov	ah, [PATH_Level]
   505 0000A8DB 80FC07              <1> 	cmp	ah, 7
   506 0000A8DE 731B                <1> 	jnb	short pass_ppdn_convert_sub_dir_name
   507 0000A8E0 FEC4                <1> 	inc	ah  
   508 0000A8E2 8825[C9670100]      <1> 	mov	[PATH_Level], ah
   509 0000A8E8 BE[CA670100]        <1> 	mov	esi, Dir_File_Name
   510                              <1> 	;mov	edi, [PATH_Array_Ptr]
   511 0000A8ED B010                <1> 	mov	al, 16
   512 0000A8EF F6E4                <1> 	mul	ah
   513 0000A8F1 8B3C24              <1> 	mov	edi, [esp]
   514                              <1> 	;push	edi 
   515 0000A8F4 01C7                <1> 	add	edi, eax
   516 0000A8F6 E82A030000          <1> 	call	convert_file_name
   517                              <1> 	;pop	edi
   518                              <1> pass_ppdn_convert_sub_dir_name:
   519 0000A8FB 89DE                <1> 	mov	esi, ebx
   520                              <1> repeat_ppdn_check_last_slash:
   521 0000A8FD AC                  <1> 	lodsb
   522 0000A8FE 3C2F                <1> 	cmp	al, '/'
   523 0000A900 74FB                <1> 	je	short repeat_ppdn_check_last_slash
   524 0000A902 3C21                <1> 	cmp	al, 21h
   525 0000A904 739D                <1> 	jnb	short loc_ppdn_get_dir_name
   526                              <1> end_of_parse_dir_name:
   527 0000A906 5F                  <1> 	pop	edi
   528 0000A907 F5                  <1> 	cmc  
   529                              <1> 	;mov	al, [PATH_CDLevel]
   530                              <1> 	;mov	ah, [PATH_Level]
   531 0000A908 66A1[C8670100]      <1> 	mov	ax, [PATH_CDLevel]
   532 0000A90E C3                  <1> 	retn
   533                              <1> 
   534                              <1> loc_ppdn_dot_dot:
   535 0000A90F AC                  <1> 	lodsb
   536 0000A910 3C21                <1> 	cmp	al, 21h
   537 0000A912 73F2                <1> 	jnb	short end_of_parse_dir_name 
   538                              <1> loc_ppdn_dot_dot_prev_level:
   539 0000A914 66A1[C8670100]      <1> 	mov	ax, [PATH_CDLevel]
   540 0000A91A 80EC01              <1> 	sub	ah, 1
   541 0000A91D 80D400              <1> 	adc	ah, 0
   542 0000A920 38E0                <1> 	cmp	al, ah
   543 0000A922 7602                <1> 	jna	short pass_ppdn_set_al_to_ah
   544 0000A924 88E0                <1> 	mov	al, ah
   545                              <1> pass_ppdn_set_al_to_ah:
   546 0000A926 66A3[C8670100]      <1> 	mov	[PATH_CDLevel], ax
   547 0000A92C EBCD                <1> 	jmp	short pass_ppdn_convert_sub_dir_name
   548                              <1> 
   549                              <1> locate_current_dir_file:
   550                              <1> 	; 20/11/2017
   551                              <1> 	; 14/02/2016
   552                              <1> 	; 13/02/2016
   553                              <1> 	; 10/02/2016
   554                              <1> 	; 06/02/2016 (TRDOS 386 = TRDOS v2.0)
   555                              <1> 	; 14/08/2010
   556                              <1> 	; 19/09/2009
   557                              <1>         ; 2005
   558                              <1> 	; INPUT ->
   559                              <1> 	;	ESI = DOS DirEntry Format FileName Address
   560                              <1> 	;	AL = Attributes Mask 
   561                              <1> 	;	(<AL AND EntryAttrib> must be equal to AL)
   562                              <1> 	;	AH = Negative Attributes Mask (If AH>0)
   563                              <1> 	;	(<AH AND EntryAttrib> must be ZERO)
   564                              <1> 	;	CH > 0 Find First Free Dir Entry or Deleted Entry
   565                              <1> 	;	CL = 0 -> Return the First Free Dir Entry
   566                              <1> 	;	CL = E5h -> Return the 1st deleted entry
   567                              <1> 	;	CL = FFh -> Return the 1st deleted or free entry
   568                              <1> 	;	CL > 0 and CL <> E5h and CL <> FFh -> Return the first 
   569                              <1> 	;	     proper entry (which fits with Atributes Masks)
   570                              <1> 	;	CX = 0 Find Valid File/Directory/VolumeName
   571                              <1> 	;	? = Any One Char
   572                              <1> 	;	* = Every Chars
   573                              <1> 	; OUTPUT ->
   574                              <1> 	;	EDI = Directory Entry Address (in Directory Buffer)
   575                              <1> 	;	ESI = DOS DirEntry Format FileName Address
   576                              <1> 	;	CF = 0 -> No Error, Proper Entry,
   577                              <1> 	;	DL = Attributes
   578                              <1> 	;	DH = Previous Entry Attr (LongName Check)
   579                              <1> 	;	AL > 0 -> Ambiguous filename wildcard "?" used
   580                              <1> 	;	AH > 0 -> Ambiguous filename wildcard "*" used
   581                              <1> 	;	AX = 0 -> Filename full fits with directory entry
   582                              <1> 	;	CH = The 1st Name Char of Current Dir Entry
   583                              <1> 	;	CF = 1 -> Proper entry not found, Error Code in EAX/AL
   584                              <1> 	;	CL = 0 and CH = 0 -> Free Entry (End Of Dir)
   585                              <1> 	;	CL = 0 and CH = E5h -> Deleted Entry fits with filters
   586                              <1> 	;	CL > 0 -> Entry not found, CH invalid
   587                              <1> 	;	CF = 0 -> 
   588                              <1> 	;	EBX = Current Directory Entry Index/Number (BX)
   589                              <1> 
   590                              <1> 	;mov	word [DirBuff_EntryCounter], 0 ; Zero Based
   591                              <1> 
   592 0000A92E 8935[2B670100]      <1> 	mov	[CDLF_FNAddress], esi
   593 0000A934 66A3[29670100]      <1> 	mov	[CDLF_AttributesMask], ax
   594 0000A93A 66890D[2F670100]    <1> 	mov	[CDLF_DEType], cx
   595                              <1> 
   596 0000A941 31DB                <1> 	xor	ebx, ebx
   597 0000A943 881D[40670100]      <1> 	mov	[PreviousAttr], bl ; 0  ; 13/02/2016
   598                              <1> 
   599 0000A949 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
   600 0000A94F 381D[6C660100]      <1> 	cmp	byte [DirBuff_ValidData], bl ; 0
   601 0000A955 761D                <1> 	jna	short loc_lcdf_reload_current_dir2
   602 0000A957 8A1D[6A660100]      <1>         mov     bl, [DirBuff_DRV]
   603 0000A95D 80EB41              <1> 	sub	bl, 'A'
   604 0000A960 38DF                <1> 	cmp	bh, bl
   605 0000A962 750E                <1> 	jne	short loc_lcdf_reload_current_dir1
   606 0000A964 8B15[71660100]      <1> 	mov	edx, [DirBuff_Cluster]
   607 0000A96A 3B15[405F0100]      <1> 	cmp	edx, [Current_Dir_FCluster]
   608 0000A970 7412                <1> 	je	short loc_cdir_locatefile_search
   609                              <1> 
   610                              <1> loc_lcdf_reload_current_dir1:
   611 0000A972 30DB                <1> 	xor	bl, bl
   612                              <1> loc_lcdf_reload_current_dir2:
   613 0000A974 89DE                <1> 	mov	esi, ebx
   614 0000A976 81C600010900        <1>         add     esi, Logical_DOSDisks
   615 0000A97C E874000000          <1> 	call	reload_current_directory 
   616 0000A981 735D                <1> 	jnc	short loc_locatefile_search_again 
   617 0000A983 C3                  <1> 	retn  
   618                              <1> 
   619                              <1> loc_cdir_locatefile_search:
   620 0000A984 31DB                <1> 	xor	ebx, ebx
   621 0000A986 55                  <1> 	push	ebp ; 20/11/2017
   622 0000A987 E8A6000000          <1> 	call	find_directory_entry
   623 0000A98C 5D                  <1> 	pop	ebp ; 20/11/2017
   624 0000A98D 7349                <1> 	jnc	short loc_cdir_locate_file_retn
   625                              <1> 
   626                              <1> loc_locatefile_check_stc_reason:
   627 0000A98F 08ED                <1> 	or	ch, ch
   628 0000A991 7444                <1> 	jz	short loc_cdir_locate_file_stc_retn
   629                              <1> 
   630                              <1> loc_locatefile_check_next_entryblock:
   631 0000A993 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
   632 0000A999 28DB                <1> 	sub	bl, bl
   633 0000A99B 0FB7F3              <1> 	movzx	esi, bx
   634 0000A99E 81C600010900        <1>         add     esi, Logical_DOSDisks
   635                              <1> 
   636 0000A9A4 803D[445F0100]00    <1> 	cmp	byte [Current_Dir_Level], 0
   637 0000A9AB 760A                <1> 	jna	short loc_locatefile_check_FAT_type
   638                              <1>             
   639 0000A9AD 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
   640 0000A9B4 730A                <1> 	jnb	short loc_locatefile_load_subdir_cluster
   641 0000A9B6 C3                  <1> 	retn  
   642                              <1> 
   643                              <1> loc_locatefile_check_FAT_type:
   644 0000A9B7 803D[455F0100]03    <1> 	cmp	byte [Current_FATType], 3
   645 0000A9BE 7218                <1> 	jb	short loc_cdir_locate_file_retn
   646                              <1> 
   647                              <1> loc_locatefile_load_subdir_cluster:
   648 0000A9C0 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
   649 0000A9C5 E83A1A0000          <1> 	call	get_next_cluster
   650 0000A9CA 730D                <1> 	jnc	short loc_locatefile_next_cluster
   651 0000A9CC 09C0                <1> 	or	eax, eax
   652 0000A9CE 7507                <1> 	jnz	short loc_locatefile_drive_not_ready_read_err
   653 0000A9D0 F9                  <1> 	stc
   654                              <1> loc_locatefile_file_notfound:
   655 0000A9D1 B802000000          <1> 	mov	eax, 2 ; File/Directory/VolName not found
   656 0000A9D6 C3                  <1> 	retn
   657                              <1> 
   658                              <1> loc_locatefile_drive_not_ready_read_err:
   659                              <1> 	;mov	eax, 17 ;Drive not ready or read error
   660                              <1> loc_cdir_locate_file_stc_retn:
   661 0000A9D7 F5                  <1> 	cmc ;stc
   662                              <1> loc_cdir_locate_file_retn:
   663 0000A9D8 C3                  <1> 	retn
   664                              <1> 
   665                              <1> loc_locatefile_next_cluster:
   666 0000A9D9 E80C1C0000          <1> 	call	load_FAT_sub_directory
   667                              <1> 	;jc	short loc_locatefile_drive_not_ready_read_err
   668 0000A9DE 72F8                <1> 	jc	short loc_cdir_locate_file_retn 
   669                              <1> 
   670                              <1> loc_locatefile_search_again:
   671 0000A9E0 8B35[2B670100]      <1> 	mov	esi, [CDLF_FNAddress] 
   672 0000A9E6 66A1[29670100]      <1> 	mov	ax, [CDLF_AttributesMask]
   673 0000A9EC 668B0D[2F670100]    <1> 	mov	cx, [CDLF_DEType] 
   674 0000A9F3 EB8F                <1> 	jmp	short loc_cdir_locatefile_search
   675                              <1> 
   676                              <1> reload_current_directory:
   677                              <1> 	; 06/02/2016 (TRDOS 386 = TRDOS v2.0)
   678                              <1> 	; 13/06/2010
   679                              <1> 	; 22/09/2009
   680                              <1>         ;
   681                              <1> 	; INPUT ->
   682                              <1> 	;	ESI = Dos drive description table address
   683                              <1> 	
   684                              <1> 	;mov	al, [esi+LD_FATType]
   685 0000A9F5 A0[455F0100]        <1> 	mov	al, [Current_FATType]
   686 0000A9FA 3C02                <1> 	cmp	al, 2
   687 0000A9FC 7729                <1> 	ja	short loc_reload_FAT_sub_directory
   688 0000A9FE 8A25[445F0100]      <1> 	mov	ah, [Current_Dir_Level]
   689 0000AA04 08C0                <1> 	or	al, al
   690 0000AA06 740A                <1> 	jz	short loc_reload_FS_directory
   691 0000AA08 08E4                <1> 	or	ah, ah
   692 0000AA0A 751B                <1> 	jnz	short loc_reload_FAT_sub_directory
   693                              <1> loc_reload_FAT_12_16_root_directory:
   694 0000AA0C E84E1B0000          <1> 	call	load_FAT_root_directory
   695 0000AA11 C3                  <1> 	retn
   696                              <1> loc_reload_FS_directory:
   697 0000AA12 20E4                <1> 	and	ah, ah
   698 0000AA14 7506                <1> 	jnz	short loc_reload_FS_sub_directory 
   699                              <1> loc_reload_FS_root_directory: 
   700 0000AA16 E80B1C0000          <1> 	call	load_FS_root_directory
   701 0000AA1B C3                  <1> 	retn
   702                              <1> loc_reload_FS_sub_directory:
   703 0000AA1C A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
   704 0000AA21 E8011C0000          <1> 	call	load_FS_sub_directory
   705 0000AA26 C3                  <1> 	retn 
   706                              <1> loc_reload_FAT_sub_directory:
   707 0000AA27 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
   708 0000AA2C E8B91B0000          <1> 	call	load_FAT_sub_directory
   709 0000AA31 C3                  <1> 	retn
   710                              <1> 
   711                              <1> find_directory_entry:
   712                              <1> 	; 14/02/2016
   713                              <1> 	; 13/02/2016
   714                              <1> 	; 10/02/2016
   715                              <1> 	; 06/02/2016 (TRDOS 386 = TRDOS v2.0)
   716                              <1> 	; 14/08/2010 (DIR.ASM, "proc_find_direntry")
   717                              <1> 	; 19/09/2009
   718                              <1> 	; 2005
   719                              <1> 	; INPUT ->
   720                              <1> 	;	ESI = Sub Dir or File Name Address
   721                              <1> 	;	AL = Attributes Mask 
   722                              <1> 	;	(<AL AND EntryAttrib> must be equal to AL)
   723                              <1> 	;	AH = Negative Attributes Mask (If AH>0)
   724                              <1> 	;	(<AH AND EntryAttrib> must be ZERO)
   725                              <1> 	;	CH > 0 Find First Free Dir Entry or Deleted Entry
   726                              <1> 	;	CL = 0 -> Return the First Free Dir Entry
   727                              <1> 	;	CL = E5h -> Return the 1st deleted entry
   728                              <1> 	;	CL = FFh -> Return the 1st deleted or free entry
   729                              <1> 	;	CL > 0 and CL <> E5h and CL <> FFh -> Return the first 
   730                              <1> 	;            proper entry (which fits with Atributes Masks)
   731                              <1> 	;	CX = 0 -> Find Valid File/Directory/VolumeName
   732                              <1> 	;	? = Any One Char
   733                              <1> 	;	* = Every Chars
   734                              <1> 	;	EBX = Current Dir Entry (BX)
   735                              <1> 	;
   736                              <1> 	; OUTPUT -> 
   737                              <1> 	;	EDI = Directory Entry Address (in DirectoryBuffer)
   738                              <1> 	;	ESI = Sub Dir or File Name Address
   739                              <1> 	;	CF = 0 -> No Error, Proper Entry,
   740                              <1> 	;	DL = Attributes
   741                              <1> 	;	DH = Previous Entry Attr (LongName Check)
   742                              <1> 	;	AL > 0 -> Ambiguous filename wildcard "?" used
   743                              <1> 	;	AH > 0 -> Ambiguous filename wildcard "*" used
   744                              <1> 	;	AX = 0 -> Filename full fits with directory entry
   745                              <1> 	;	EBX = CurrentDirEntry (BX)
   746                              <1> 	;	CH = The 1st Name Char of Current Dir Entry
   747                              <1> 	;	CF = 1 -> Proper entry not found, Error Code in AX/AL
   748                              <1> 	;	CL = 0 and CH = 0 -> Free Entry (End Of Dir)
   749                              <1> 	;	CL = 0 and CH = E5h -> Deleted Entry fits with filters
   750                              <1> 	;	CL > 0 -> Entry not found, CH invalid
   751                              <1> 	;
   752                              <1> 	; (EAX, EBX, ECX, EDX, EDI, EBP will be changed)	 
   753                              <1> 
   754 0000AA32 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
   755 0000AA39 0F8739010000        <1>         ja      loc_ffde_stc_retn_255
   756                              <1> 
   757                              <1> 	;mov    [DirBuff_CurrentEntry], bx  
   758                              <1> 
   759 0000AA3F BF00000800          <1>   	mov	edi, Directory_Buffer
   760 0000AA44 66A3[3C670100]      <1> 	mov	[FDE_AttrMask], ax
   761                              <1> 
   762 0000AA4A 29C0                <1> 	sub	eax, eax
   763                              <1>             
   764                              <1> 	;;mov	[PreviousAttr], al ; 0 ;; 13/02/2016
   765 0000AA4C 66A3[3E670100]      <1> 	mov	[AmbiguousFileName], ax ; 0
   766                              <1> 
   767 0000AA52 6689D8              <1> 	mov	ax, bx
   768 0000AA55 66C1E005            <1> 	shl	ax, 5 ; ; * 32 ; Directory entry size
   769 0000AA59 01C7                <1> 	add     edi, eax
   770                              <1> 
   771 0000AA5B 08ED                <1> 	or	ch, ch
   772 0000AA5D 0F852C010000        <1>         jnz     loc_find_free_deleted_entry_0
   773                              <1> 
   774 0000AA63 08C9                <1> 	or      cl, cl
   775 0000AA65 0F850D010000        <1>         jnz     loc_ffde_stc_retn_255
   776                              <1>  
   777                              <1> check_find_dir_entry:
   778 0000AA6B 66A1[3C670100]      <1> 	mov	ax, [FDE_AttrMask]
   779 0000AA71 8A2F                <1> 	mov	ch, [edi]
   780 0000AA73 80FD00              <1> 	cmp     ch, 0 ; Is it never used entry?
   781 0000AA76 0F86FF000000        <1> 	jna	loc_find_direntry_stc_retn 
   782 0000AA7C 56                  <1> 	push	esi
   783 0000AA7D 8A570B              <1> 	mov	dl, [edi+0Bh] ; File attributes
   784 0000AA80 80FDE5              <1> 	cmp	ch, 0E5h ; Is it a deleted file?
   785 0000AA83 746D                <1> 	je	short loc_find_dir_next_entry_prevdeleted
   786                              <1> 
   787 0000AA85 80FA0F              <1> 	cmp     dl, 0Fh ; longname sub component check
   788 0000AA88 7505                <1> 	jne     short loc_check_attributes_mask
   789 0000AA8A E8ED010000          <1> 	call	save_longname_sub_component
   790                              <1> 
   791                              <1> loc_check_attributes_mask:
   792 0000AA8F 88C6                <1> 	mov	dh, al
   793 0000AA91 20D6                <1> 	and	dh, dl    
   794 0000AA93 38F0                <1> 	cmp	al, dh
   795 0000AA95 0F85BA000000        <1>         jne     loc_find_dir_next_entry
   796 0000AA9B 20D4                <1> 	and	ah, dl
   797 0000AA9D 0F85B2000000        <1>         jnz     loc_find_dir_next_entry
   798 0000AAA3 80FA0F              <1> 	cmp	dl, 0Fh
   799 0000AAA6 751A                <1> 	jne	short pass_direntry_attr_check
   800                              <1> 
   801 0000AAA8 3C0F                <1> 	cmp	al, 0Fh ; AL = 0Fh -> find long name
   802 0000AAAA 0F85A5000000        <1>         jne     loc_find_dir_next_entry
   803                              <1> 
   804 0000AAB0 5E                  <1> 	pop	esi
   805 0000AAB1 6631C0              <1> 	xor	ax, ax
   806 0000AAB4 8A35[40670100]      <1> 	mov	dh, [PreviousAttr]
   807 0000AABA 66891D[6D660100]    <1> 	mov	[DirBuff_CurrentEntry], bx
   808 0000AAC1 C3                  <1> 	retn
   809                              <1> 
   810                              <1> pass_direntry_attr_check:
   811 0000AAC2 89FD                <1> 	mov	ebp, edi ; 14/02/2016
   812 0000AAC4 B908000000          <1> 	mov	ecx, 8
   813                              <1> loc_lodsb_find_dir:
   814 0000AAC9 AC                  <1> 	lodsb
   815 0000AACA 3C2A                <1> 	cmp	al, '*'
   816 0000AACC 7508                <1> 	jne	short pass_fde_ambiguous1_check
   817 0000AACE FE05[3F670100]      <1>         inc     byte [AmbiguousFileName+1]
   818 0000AAD4 EB28                <1> 	jmp	short loc_check_direntry_extension
   819                              <1> 
   820                              <1> pass_fde_ambiguous1_check:
   821 0000AAD6 3C3F                <1> 	cmp	al, '?'
   822 0000AAD8 750D                <1> 	jne	short pass_fde_ambiguous2_check
   823 0000AADA FE05[3E670100]      <1> 	inc	byte [AmbiguousFileName]
   824 0000AAE0 803F20              <1> 	cmp	byte [edi], 20h
   825 0000AAE3 764E                <1> 	jna	short loc_find_dir_next_entry_ebp
   826 0000AAE5 EB14                <1> 	jmp	short loc_scasb_find_dir_inc_di
   827                              <1> 
   828                              <1> pass_fde_ambiguous2_check:
   829 0000AAE7 3C20                <1> 	cmp	al, 20h
   830 0000AAE9 750C                <1> 	jne	short loc_scasb_find_dir
   831 0000AAEB 803F20              <1> 	cmp	byte [edi], 20h
   832 0000AAEE 7543                <1> 	jne	short loc_find_dir_next_entry_ebp
   833 0000AAF0 EB0C                <1> 	jmp	short loc_check_direntry_extension
   834                              <1> 
   835                              <1> loc_find_dir_next_entry_prevdeleted:
   836 0000AAF2 80CA80              <1> 	or	dl, 80h  ; Bit 7 -> deleted entry sign
   837 0000AAF5 EB5E                <1> 	jmp	short loc_find_dir_next_entry
   838                              <1> 
   839                              <1> loc_scasb_find_dir:
   840 0000AAF7 3A07                <1> 	cmp	al, [edi]
   841 0000AAF9 7538                <1> 	jne	short loc_find_dir_next_entry_ebp
   842                              <1> loc_scasb_find_dir_inc_di:
   843 0000AAFB 47                  <1> 	inc	edi
   844 0000AAFC E2CB                <1> 	loop	loc_lodsb_find_dir
   845                              <1> 
   846                              <1> loc_check_direntry_extension:
   847 0000AAFE BE08000000          <1> 	mov	esi, 8
   848 0000AB03 89F7                <1> 	mov	edi, esi ; 8
   849 0000AB05 033424              <1> 	add	esi, [esp] ; Sub Dir or File Name Address
   850 0000AB08 01EF                <1> 	add	edi, ebp
   851 0000AB0A B103                <1> 	mov	cl, 3
   852                              <1> loc_lodsb_find_dir_ext:
   853 0000AB0C AC                  <1> 	lodsb
   854 0000AB0D 3C2A                <1> 	cmp	al, '*'
   855 0000AB0F 7508                <1> 	jne	short pass_fde_ambiguous3_check
   856 0000AB11 FE05[3F670100]      <1> 	inc	byte [AmbiguousFileName+1]
   857 0000AB17 EB1E                <1> 	jmp	short loc_find_dir_proper_direntry
   858                              <1> 
   859                              <1> pass_fde_ambiguous3_check:
   860 0000AB19 3C3F                <1> 	cmp	al, '?'
   861 0000AB1B 750D                <1> 	jne	short pass_fde_ambiguous4_check
   862 0000AB1D FE05[3E670100]      <1> 	inc	byte [AmbiguousFileName]
   863 0000AB23 803F20              <1> 	cmp	byte [edi], 20h
   864 0000AB26 760B                <1> 	jna	short loc_find_dir_next_entry_ebp
   865 0000AB28 EB49                <1> 	jmp	short loc_scasb_find_dir_ext_inc_di
   866                              <1> 
   867                              <1> pass_fde_ambiguous4_check:
   868 0000AB2A 3C20                <1> 	cmp	al, 20h
   869 0000AB2C 7541                <1> 	jne	short loc_scasb_find_dir_ext
   870 0000AB2E 803F20              <1> 	cmp	byte [edi], 20h
   871 0000AB31 7404                <1> 	je	short loc_find_dir_proper_direntry
   872                              <1> 
   873                              <1> loc_find_dir_next_entry_ebp:
   874 0000AB33 89EF                <1> 	mov	edi, ebp ; 14/02/2016
   875 0000AB35 EB1E                <1> 	jmp	short loc_find_dir_next_entry
   876                              <1> 
   877                              <1> loc_find_dir_proper_direntry:
   878 0000AB37 30C9                <1> 	xor	cl, cl
   879                              <1> loc_find_dir_proper_direntry_1:
   880 0000AB39 5E                  <1> 	pop	esi
   881 0000AB3A 89EF                <1>         mov     edi, ebp
   882 0000AB3C 8A2F                <1> 	mov	ch, [edi]
   883 0000AB3E 8A570B              <1> 	mov     dl, [edi+0Bh] ; Dir entry attributes
   884 0000AB41 66A1[3E670100]      <1> 	mov	ax, [AmbiguousFileName]
   885                              <1> loc_find_dir_proper_direntry_2:
   886 0000AB47 8A35[40670100]      <1> 	mov     dh, [PreviousAttr]
   887 0000AB4D 66891D[6D660100]    <1> 	mov	[DirBuff_CurrentEntry], bx
   888 0000AB54 C3                  <1> 	retn
   889                              <1> 
   890                              <1> loc_find_dir_next_entry:
   891 0000AB55 8815[40670100]      <1> 	mov	byte [PreviousAttr], dl ; LongName check
   892                              <1> loc_find_dir_next_entry_1:
   893 0000AB5B 5E                  <1> 	pop	esi
   894 0000AB5C 83C720              <1> 	add	edi, 32
   895                              <1> 	;inc	word [DirBuff_EntryCounter]
   896 0000AB5F 6643                <1> 	inc	bx
   897 0000AB61 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
   898 0000AB68 770E                <1> 	ja	short loc_ffde_stc_retn_255
   899 0000AB6A E9FCFEFFFF          <1>         jmp     check_find_dir_entry 
   900                              <1> 
   901                              <1> loc_scasb_find_dir_ext:
   902 0000AB6F 3A07                <1> 	cmp	al, [edi]
   903 0000AB71 75C0                <1> 	jne	short loc_find_dir_next_entry_ebp
   904                              <1> loc_scasb_find_dir_ext_inc_di:
   905 0000AB73 47                  <1> 	inc	edi
   906 0000AB74 E296                <1> 	loop    loc_lodsb_find_dir_ext
   907 0000AB76 EBC1                <1> 	jmp	short loc_find_dir_proper_direntry_1
   908                              <1> 
   909                              <1> loc_ffde_stc_retn_255:
   910                              <1> 	;mov	cx, 0FFFFh
   911 0000AB78 31C9                <1> 	xor	ecx, ecx
   912 0000AB7A 49                  <1> 	dec	ecx ; 0FFFFFFFFh
   913                              <1> 	;xor	eax, eax
   914                              <1> loc_find_direntry_stc_retn:
   915                              <1> loc_check_ffde_retn_1:
   916                              <1> 	;mov	ax, 2
   917 0000AB7B B802000000          <1> 	mov	eax, 2 ; File Not Found
   918 0000AB80 8A35[40670100]      <1> 	mov	dh, [PreviousAttr]
   919 0000AB86 66891D[6D660100]    <1> 	mov	[DirBuff_CurrentEntry], bx
   920 0000AB8D F9                  <1> 	stc
   921 0000AB8E C3                  <1> 	retn
   922                              <1> 
   923                              <1> loc_find_free_deleted_entry_0:
   924 0000AB8F 66A1[3C670100]      <1> 	mov	ax, [FDE_AttrMask]
   925 0000AB95 8A2F                <1> 	mov	ch, [edi]
   926 0000AB97 8A570B              <1> 	mov	dl, [edi+0Bh] ; File attributes
   927 0000AB9A 08C9                <1> 	or	cl, cl 
   928 0000AB9C 7407                <1> 	jz	short loc_check_ffde_0_repeat
   929                              <1> 	;cmp	cl, 0E5h
   930                              <1> 	;je	short pass_loc_check_ffde_0_err
   931 0000AB9E 80F9FF              <1> 	cmp	cl, 0FFh
   932 0000ABA1 7432                <1> 	je	short loc_find_free_deleted_entry_1
   933 0000ABA3 EB4D                <1> 	jmp	short pass_loc_check_ffde_0_err
   934                              <1> 
   935                              <1> loc_check_ffde_0_repeat:
   936 0000ABA5 08ED                <1> 	or	ch, ch
   937 0000ABA7 7511                <1> 	jnz	short loc_check_ffde_0_next
   938                              <1> 
   939                              <1> loc_check_ffde_retn_2:
   940 0000ABA9 6629C0              <1> 	sub	ax, ax
   941 0000ABAC 8A35[40670100]      <1> 	mov	dh, [PreviousAttr]
   942 0000ABB2 66891D[6D660100]    <1> 	mov	[DirBuff_CurrentEntry], bx
   943 0000ABB9 C3                  <1> 	retn
   944                              <1>  
   945                              <1> loc_check_ffde_0_next:
   946 0000ABBA 6643                <1> 	inc	bx
   947 0000ABBC 83C720              <1> 	add	edi, 32
   948                              <1> 	;inc	word [DirBuff_EntryCounter]
   949                              <1> 	 
   950 0000ABBF 663B1D[6F660100]    <1>         cmp	bx, [DirBuff_LastEntry]
   951 0000ABC6 77B0                <1> 	ja	short loc_ffde_stc_retn_255
   952 0000ABC8 8815[40670100]      <1> 	mov	[PreviousAttr], dl
   953 0000ABCE 8A2F                <1> 	mov	ch, [edi]
   954 0000ABD0 8A570B              <1> 	mov	dl, [edi+0Bh] ; file attributes
   955 0000ABD3 EBD0                <1> 	jmp	short loc_check_ffde_0_repeat
   956                              <1> 
   957                              <1> loc_find_free_deleted_entry_1:
   958 0000ABD5 28D2                <1> 	sub	dl, dl      
   959                              <1> loc_find_free_deleted_entry_2:
   960 0000ABD7 20ED                <1> 	and	ch, ch  
   961 0000ABD9 74CE                <1> 	jz	short loc_check_ffde_retn_2
   962 0000ABDB 80FDE5              <1> 	cmp	ch, 0E5h
   963 0000ABDE 74C9                <1> 	je	short loc_check_ffde_retn_2
   964 0000ABE0 6643                <1> 	inc	bx
   965 0000ABE2 83C720              <1> 	add	edi, 32
   966 0000ABE5 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
   967 0000ABEC 778A                <1> 	ja	short loc_ffde_stc_retn_255
   968 0000ABEE 8A2F                <1> 	mov	ch, [edi]
   969 0000ABF0 EBE5                <1> 	jmp	short loc_find_free_deleted_entry_2
   970                              <1> 
   971                              <1> pass_loc_check_ffde_0_err:
   972 0000ABF2 38CD                <1> 	cmp	ch, cl
   973 0000ABF4 741F                <1> 	je	short loc_check_ffde_attrib 
   974                              <1> 
   975 0000ABF6 6643                <1> 	inc	bx
   976 0000ABF8 83C720              <1> 	add	edi, 32
   977 0000ABFB 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
   978 0000AC02 0F8770FFFFFF        <1>         ja      loc_ffde_stc_retn_255
   979 0000AC08 8815[40670100]      <1> 	mov	[PreviousAttr], dl
   980 0000AC0E 8A2F                <1> 	mov	ch, [edi]
   981 0000AC10 8A570B              <1> 	mov	dl, [edi+0Bh]
   982 0000AC13 EBDD                <1> 	jmp	short pass_loc_check_ffde_0_err
   983                              <1> 
   984                              <1> loc_check_ffde_attrib:
   985 0000AC15 88C6                <1> 	mov	dh, al
   986 0000AC17 20D6                <1> 	and	dh, dl    
   987 0000AC19 38F0                <1> 	cmp	al, dh
   988 0000AC1B 759D                <1> 	jne	short loc_check_ffde_0_next
   989 0000AC1D 20D4                <1> 	and	ah, dl
   990 0000AC1F 7599                <1> 	jnz	short loc_check_ffde_0_next
   991 0000AC21 30C9                <1> 	xor	cl, cl 
   992 0000AC23 EB84                <1>         jmp     loc_check_ffde_retn_2
   993                              <1> 
   994                              <1> convert_file_name:
   995                              <1> 	; 06/03/2016
   996                              <1> 	; 11/02/2016
   997                              <1> 	; 07/02/2016 (TRDOS 386 = TRDOS v2.0)
   998                              <1> 	; 06/10/2009
   999                              <1> 	; 2005
  1000                              <1> 	;
  1001                              <1> 	; INPUT  ->
  1002                              <1> 	;	ESI = Dot File Name Location
  1003                              <1> 	;	EDI = Dir Entry Format File Name Location
  1004                              <1> 	; OUTPUT ->
  1005                              <1> 	;	EDI = Dir Entry Format File Name Location
  1006                              <1> 	;	ESI = Dot File Name Location (capitalized)
  1007                              <1> 	;
  1008                              <1> 	; (ECX, AL will be changed) 
  1009                              <1>      
  1010 0000AC25 56                  <1> 	push	esi  
  1011 0000AC26 57                  <1> 	push	edi
  1012                              <1> 
  1013 0000AC27 B90B000000          <1> 	mov	ecx, 11
  1014 0000AC2C B020                <1> 	mov	al, 20h
  1015 0000AC2E F3AA                <1> 	rep	stosb
  1016                              <1> 
  1017 0000AC30 8B3C24              <1> 	mov	edi, [esp]
  1018                              <1> 
  1019 0000AC33 B10C                <1> 	mov	cl, 12 ; file name length (max.)
  1020                              <1> 	; 06/03/2016
  1021                              <1> 	; Directory entry name limit (11 bytes) check for
  1022                              <1> 	; 'rename_directory_entry' procedure.
  1023                              <1> 	; (EDI points to Directory Entry)
  1024                              <1> 	; (If the file name would not contain a dot
  1025                              <1> 	; and file name length would be 12, this would cause to
  1026                              <1> 	; overwrite the attributes byte of the directory entry.)
  1027                              <1> 	;
  1028 0000AC35 B50B                <1> 	mov	ch, 11 ; directory entry's name length
  1029                              <1> loc_check_first_dot:
  1030 0000AC37 8A06                <1> 	mov	al, [esi]
  1031 0000AC39 3C2E                <1> 	cmp	al, 2Eh
  1032 0000AC3B 750C                <1> 	jne	short pass_check_first_dot
  1033 0000AC3D 8807                <1> 	mov	[edi], al
  1034 0000AC3F 47                  <1> 	inc	edi
  1035 0000AC40 46                  <1> 	inc	esi
  1036 0000AC41 FEC9                <1> 	dec	cl
  1037 0000AC43 75F2                <1> 	jnz	short loc_check_first_dot
  1038                              <1> 	;;(ecx <= 12)
  1039                              <1> 	;;loop	loc_check_first_dot 
  1040 0000AC45 EB30                <1> 	jmp	short stop_convert_file
  1041                              <1> 
  1042                              <1> loc_get_fchar:
  1043 0000AC47 8A06                <1> 	mov	al, [esi]
  1044                              <1> pass_check_first_dot:
  1045 0000AC49 3C61                <1> 	cmp	al, 61h ; 'a'
  1046 0000AC4B 7208                <1> 	jb	short pass_name_capitalize
  1047 0000AC4D 3C7A                <1> 	cmp	al, 7Ah ; 'z'
  1048 0000AC4F 7704                <1> 	ja	short pass_name_capitalize
  1049 0000AC51 24DF                <1> 	and	al, 0DFh
  1050 0000AC53 8806                <1> 	mov	[esi], al
  1051                              <1> pass_name_capitalize:
  1052 0000AC55 3C21                <1> 	cmp	al, 21h
  1053 0000AC57 721E                <1> 	jb	short stop_convert_file
  1054 0000AC59 3C2E                <1> 	cmp	al, 2Eh ; '.'
  1055 0000AC5B 750C                <1> 	jne	short pass_dot_space
  1056                              <1> add_dot_space: 
  1057 0000AC5D 80F904              <1> 	cmp	cl, 4
  1058 0000AC60 760E                <1> 	jna	short inc_and_loop
  1059 0000AC62 47                  <1> 	inc	edi
  1060 0000AC63 FECD                <1> 	dec	ch ; 06/03/2016
  1061 0000AC65 FEC9                <1> 	dec	cl
  1062 0000AC67 EBF4                <1> 	jmp	short add_dot_space
  1063                              <1> 	
  1064                              <1> 	;mov	al, 4
  1065                              <1> 	;cmp	cl, al
  1066                              <1> 	;jna	short inc_and_loop
  1067                              <1> 	;sub	cl, al
  1068                              <1> 	;add	edi, ecx
  1069                              <1> 	;mov	cl, al
  1070                              <1> 	;jmp	short inc_and_loop	
  1071                              <1> 
  1072                              <1> pass_dot_space:
  1073 0000AC69 8807                <1> 	mov	[edi], al
  1074                              <1> loc_after_double_dot:
  1075                              <1> 	; 06/03/2016
  1076 0000AC6B FECD                <1> 	dec	ch ; count down for 11 bytes dir entry limit
  1077 0000AC6D 740A                <1> 	jz	short stop_convert_file_x
  1078 0000AC6F 47                  <1> 	inc	edi
  1079                              <1> inc_and_loop:
  1080 0000AC70 FEC9                <1> 	dec	cl ; count down for 12 bytes filename limit 
  1081 0000AC72 7403                <1> 	jz	short stop_convert_file	
  1082 0000AC74 46                  <1> 	inc	esi
  1083                              <1> 	;;(ecx <= 12)
  1084                              <1> 	;;loop	loc_get_fchar
  1085 0000AC75 EBD0                <1> 	jmp	short loc_get_fchar
  1086                              <1> 
  1087                              <1> stop_convert_file:
  1088                              <1> 	; 06/03/2016
  1089 0000AC77 30ED                <1> 	xor	ch, ch
  1090                              <1> 	; ECX < 256 ; 'find_first_file' -> xor cl, cl
  1091                              <1> stop_convert_file_x:
  1092 0000AC79 5F                  <1> 	pop	edi
  1093 0000AC7A 5E                  <1> 	pop	esi
  1094 0000AC7B C3                  <1> 	retn
  1095                              <1>  
  1096                              <1> save_longname_sub_component:
  1097                              <1> 	; 13/02/2016
  1098                              <1> 	; 06/02/2016 (TRDOS 386 = TRDOS v2.0)
  1099                              <1> 	; 28/02/2010
  1100                              <1> 	; 17/10/2009
  1101                              <1> 	; INPUT ->
  1102                              <1> 	;	EDI = Directory Entry    
  1103                              <1> 	;     	// This procedure is called
  1104                              <1> 	;	// from 'find_directory_entry' procedure.
  1105                              <1> 	;	// If the last entry returns with
  1106                              <1> 	;	// a non-zero LongnameFound value and
  1107                              <1> 	;	// if LFN_CheckSum value is equal to
  1108                              <1> 	;	// the next shortname checksum,
  1109                              <1> 	;	// long name is valid.
  1110                              <1> 	;	// If a longname is longer than 65 bytes,
  1111                              <1> 	;	// it is invalid for trdos. (>45h)
  1112                              <1>  
  1113 0000AC7C 57                  <1> 	push	edi
  1114 0000AC7D 56                  <1> 	push	esi
  1115                              <1> 	;push	ebx
  1116                              <1> 	;push	ecx
  1117                              <1> 	;push	edx
  1118 0000AC7E 50                  <1> 	push	eax
  1119                              <1>            
  1120 0000AC7F 29C9                <1> 	sub	ecx, ecx
  1121                              <1> 	;sub	eax, eax
  1122 0000AC81 B11A                <1> 	mov	cl, 26
  1123                              <1> 
  1124 0000AC83 0FB607              <1> 	movzx	eax, byte [edi] ; LDIR_Order
  1125 0000AC86 3C41                <1> 	cmp	al, 41h  ; 40h (last long entry sign) + 1
  1126 0000AC88 722B                <1> 	jb	short pass_pslnsc_last_long_entry
  1127                              <1> 
  1128 0000AC8A 88C4                <1> 	mov	ah, al
  1129 0000AC8C 80EC40              <1> 	sub	ah, 40h
  1130 0000AC8F 8825[42670100]      <1> 	mov	[LFN_EntryLength], ah
  1131                              <1> 	
  1132 0000AC95 3C45                <1> 	cmp	al, 45h  ; 40h (last long entry sign) + 5
  1133                              <1>  		; Max 130 byte length is usable in TRDOS
  1134                              <1> ; 26*5 = 130
  1135 0000AC97 7753                <1> 	ja	short loc_pslnsc_retn
  1136                              <1> 
  1137 0000AC99 2407                <1> 	and	al, 07h ; 0Fh
  1138 0000AC9B A2[41670100]        <1> 	mov	[LongNameFound], al
  1139                              <1> 
  1140 0000ACA0 FEC8                <1> 	dec	al
  1141                              <1> 	;mov	cl, 26
  1142 0000ACA2 F6E1                <1> 	mul	cl
  1143                              <1> 
  1144 0000ACA4 89C6                <1> 	mov	esi, eax
  1145 0000ACA6 01CE                <1> 	add	esi, ecx
  1146                              <1> 		; to make is an ASCIIZ string
  1147                              <1> 		; with ax+26 bytes length
  1148 0000ACA8 81C6[44670100]      <1> 	add	esi, LongFileName
  1149 0000ACAE 66C7060000          <1> 	mov	word [esi], 0   
  1150 0000ACB3 EB16                <1> 	jmp	short loc_pslsc_move_ldir_name2 
  1151                              <1> 
  1152                              <1> pass_pslnsc_last_long_entry:
  1153 0000ACB5 3C04                <1> 	cmp	al, 04h
  1154 0000ACB7 7733                <1> 	ja	short loc_pslnsc_retn
  1155 0000ACB9 FE0D[41670100]      <1> 	dec	byte [LongNameFound]
  1156 0000ACBF 3A05[41670100]      <1> 	cmp	al, [LongNameFound]
  1157 0000ACC5 7525                <1> 	jne	short loc_pslnsc_retn
  1158                              <1> 
  1159                              <1> loc_pslsc_move_ldir_name1:
  1160 0000ACC7 FEC8                <1> 	dec	al
  1161                              <1> 	;mov	cl, 26
  1162 0000ACC9 F6E1                <1> 	mul	cl
  1163                              <1> 
  1164                              <1> loc_pslsc_move_ldir_name2:
  1165 0000ACCB 8A4F0D              <1> 	mov	cl, [edi+0Dh] ; long name checksum
  1166 0000ACCE 880D[43670100]      <1> 	mov	[LFN_CheckSum], cl 
  1167 0000ACD4 89FE                <1> 	mov	esi, edi ; LDIR_Order
  1168 0000ACD6 BF[44670100]        <1> 	mov	edi, LongFileName
  1169 0000ACDB 01C7                <1> 	add	edi, eax
  1170 0000ACDD 46                  <1> 	inc	esi
  1171 0000ACDE B105                <1> 	mov	cl, 5 ; chars 1 to 5
  1172 0000ACE0 F366A5              <1> 	rep	movsw
  1173 0000ACE3 83C603              <1> 	add	esi, 3
  1174 0000ACE6 A5                  <1> 	movsd	; char 6 & 7 
  1175 0000ACE7 A5                  <1> 	movsd	; char 8 & 9
  1176 0000ACE8 A5                  <1> 	movsd	; char 10 & 11
  1177 0000ACE9 46                  <1> 	inc	esi
  1178 0000ACEA 46                  <1> 	inc	esi 
  1179 0000ACEB A5                  <1> 	movsd   ; char 12 & 13 
  1180                              <1> 
  1181                              <1> loc_pslnsc_retn:
  1182 0000ACEC 58                  <1>  	pop	eax
  1183                              <1> 	;pop	edx
  1184                              <1> 	;pop	ecx
  1185                              <1> 	;pop	ebx
  1186 0000ACED 5E                  <1> 	pop	esi  
  1187 0000ACEE 5F                  <1> 	pop	edi
  1188                              <1>  
  1189 0000ACEF C3                  <1>     	retn
  1190                              <1> 
  1191                              <1> parse_path_name:
  1192                              <1> 	; 10/02/2016
  1193                              <1> 	; 08/02/2016 (TRDOS 386 = TRDOS v2.0)
  1194                              <1> 	; 10/009/2011 ('proc_parse_pathname')
  1195                              <1> 	; 27/11/2009
  1196                              <1> 	; 05/12/2004
  1197                              <1> 	;
  1198                              <1> 	; INPUT ->
  1199                              <1> 	;	ESI = Beginning of ASCIIZ pathname string
  1200                              <1> 	;       EDI = Destination Address
  1201                              <1> 	;	      (which is TR-DOS FindFile data buffer)
  1202                              <1> 	; OUTPUT ->
  1203                              <1> 	;	CF = 1 -> Error
  1204                              <1> 	;	     EAX = Error Code (AL)
  1205                              <1> 	;
  1206                              <1> 	; (Modified registers: eax, ecx, esi, edi) 
  1207                              <1> 	
  1208                              <1> 	; Clear the pathname bytes in TR-DOS Findfile data buffer 
  1209 0000ACF0 57                  <1> 	push	edi
  1210 0000ACF1 B914000000          <1> 	mov	ecx, 20  ; 80 bytes
  1211 0000ACF6 31C0                <1> 	xor	eax, eax
  1212 0000ACF8 F3AB                <1> 	rep	stosd 
  1213 0000ACFA 5F                  <1> 	pop	edi
  1214                              <1> 
  1215 0000ACFB 668B06              <1> 	mov	ax, [esi]
  1216 0000ACFE 80FC3A              <1> 	cmp	ah, ':'
  1217 0000AD01 741C                <1> 	je	short loc_ppn_change_drive
  1218 0000AD03 A0[465F0100]        <1> 	mov	al, [Current_Drv]
  1219 0000AD08 EB33                <1> 	jmp	short pass_ppn_change_drive
  1220                              <1> 
  1221                              <1> pass_ppn_cdir:
  1222 0000AD0A 8B35[66680100]      <1> 	mov	esi, [First_Path_Pos]
  1223 0000AD10 AC                  <1> 	lodsb
  1224                              <1> loc_ppn_get_filename:
  1225 0000AD11 83C741              <1> 	add	edi, 65 ; FindFile_Name location
  1226                              <1> 	; TRDOS Filename length must not be more than 12 bytes
  1227                              <1> 	;mov	ecx, 12
  1228 0000AD14 B10C                <1> 	mov	cl, 12
  1229                              <1> loc_ppn_get_fnchar_next:
  1230 0000AD16 AA                  <1> 	stosb
  1231 0000AD17 AC                  <1> 	lodsb
  1232 0000AD18 3C21                <1> 	cmp	al, 21h
  1233 0000AD1A 7274                <1> 	jb	short loc_ppn_clc_return 
  1234 0000AD1C E2F8                <1>         loop    loc_ppn_get_fnchar_next
  1235                              <1> loc_ppn_return:
  1236 0000AD1E C3                  <1> 	retn
  1237                              <1> 
  1238                              <1> loc_ppn_change_drive:
  1239 0000AD1F 24DF                <1> 	and	al, 0DFh
  1240 0000AD21 2C41                <1> 	sub	al, 'A'; A:
  1241 0000AD23 726F                <1> 	jc	short loc_ppn_invalid_drive
  1242 0000AD25 3805[C6120100]      <1> 	cmp	[Last_DOS_DiskNo], al
  1243 0000AD2B 7267                <1> 	jb	short loc_ppn_invalid_drive
  1244                              <1> 
  1245 0000AD2D 46                  <1> 	inc	esi
  1246 0000AD2E 46                  <1> 	inc	esi
  1247 0000AD2F 8A26                <1> 	mov	ah, [esi]
  1248 0000AD31 80FC21              <1> 	cmp	ah, 21h
  1249 0000AD34 7307                <1> 	jnb	short pass_ppn_change_drive
  1250                              <1> 
  1251                              <1> loc_ppn_cmd_failed:
  1252                              <1> 	; File or directory name is not existing
  1253 0000AD36 8807                <1> 	mov	[edi], al ; Drv 
  1254 0000AD38 66B80100            <1> 	mov	ax, 1 ; eax = 1
  1255                              <1> 	; TR-DOS Error Code 01h = Bad Command Argument
  1256                              <1> 	; MS-DOS Error Code 01h : Invalid Function Number
  1257                              <1> 	;stc
  1258                              <1> 	; (MainProg ErrMsg: "Bad command or file name!")
  1259 0000AD3C C3                  <1> 	retn
  1260                              <1> 
  1261                              <1> pass_ppn_change_drive:
  1262 0000AD3D 8935[66680100]      <1> 	mov	[First_Path_Pos], esi
  1263 0000AD43 C705[6A680100]0000- <1> 	mov	dword [Last_Slash_Pos], 0
  1263 0000AD4B 0000                <1>
  1264 0000AD4D AA                  <1> 	stosb
  1265 0000AD4E 8A06                <1> 	mov	al, [esi]
  1266                              <1> loc_scan_ppn_dslash:
  1267 0000AD50 3C2F                <1> 	cmp	al, '/'
  1268 0000AD52 7506                <1>   	jne	short loc_scan_next_slash_pos
  1269 0000AD54 8935[6A680100]      <1> 	mov	[Last_Slash_Pos], esi
  1270                              <1> loc_scan_next_slash_pos:
  1271 0000AD5A 46                  <1> 	inc	esi
  1272 0000AD5B 8A06                <1> 	mov	al, [esi]
  1273 0000AD5D 3C20                <1> 	cmp	al, 20h
  1274 0000AD5F 77EF                <1> 	ja	short loc_scan_ppn_dslash
  1275 0000AD61 833D[6A680100]00    <1> 	cmp	dword [Last_Slash_Pos], 0
  1276 0000AD68 76A0                <1> 	jna	short pass_ppn_cdir
  1277                              <1> 	
  1278 0000AD6A 8B0D[6A680100]      <1> 	mov	ecx, [Last_Slash_Pos]
  1279 0000AD70 8B35[66680100]      <1> 	mov	esi, [First_Path_Pos]
  1280 0000AD76 29F1                <1> 	sub	ecx, esi
  1281 0000AD78 41                  <1> 	inc	ecx
  1282                              <1> 	;cmp	ecx, 64
  1283 0000AD79 80F940              <1> 	cmp	cl, 64
  1284 0000AD7C 7715                <1> 	ja	short loc_ppn_invalid_drive_stc
  1285                              <1> 
  1286 0000AD7E 89F8                <1> 	mov	eax, edi ; Dest Dir String Location (65 byte)
  1287 0000AD80 F3A4                <1> 	rep	movsb
  1288                              <1> 	;mov	[edi], cl ; 0, End of Dir String
  1289 0000AD82 8B35[6A680100]      <1> 	mov	esi, [Last_Slash_Pos]
  1290 0000AD88 46                  <1> 	inc	esi
  1291 0000AD89 89C7                <1> 	mov	edi, eax
  1292 0000AD8B AC                  <1> 	lodsb
  1293 0000AD8C 3C21                <1> 	cmp	al, 21h
  1294 0000AD8E 7381                <1> 	jnb	short loc_ppn_get_filename
  1295                              <1> loc_ppn_clc_return:
  1296                              <1> 	;clc
  1297 0000AD90 31C0                <1> 	xor	eax, eax
  1298 0000AD92 C3                  <1> 	retn
  1299                              <1> 
  1300                              <1> loc_ppn_invalid_drive_stc:
  1301 0000AD93 F5                  <1> 	cmc	 ; stc
  1302                              <1> loc_ppn_invalid_drive:
  1303                              <1> 	; cf = 1
  1304                              <1> 	; The Drive Letter/Char < "A" or > "Z"
  1305 0000AD94 66B80F00            <1> 	mov	ax, 0Fh
  1306                              <1> 	; MS-DOS Error Code 0Fh = Disk Drive Invalid 
  1307                              <1> 	; (MainProg ErrMsg: "Drive not ready or read error!")
  1308 0000AD98 C3                  <1> 	retn
  1309                              <1> 
  1310                              <1> find_longname:
  1311                              <1> 	; 13/02/2016 (TRDOS 386 = TRDOS v2.0)
  1312                              <1> 	; 24/01/2010 (DIR.ASM, 'proc_find_longname')
  1313                              <1> 	; 17/10/2009
  1314                              <1> 	
  1315                              <1> 	; INPUT -> 
  1316                              <1> 	;	ESI = DOS short file name address
  1317                              <1> 	; 	for example: "filename.ext"
  1318                              <1> 	;
  1319                              <1> 	; OUTPUT ->
  1320                              <1> 	; 	ESI = ASCIIZ longname address (cf = 0)
  1321                              <1> 	;	cf = 1 -> error number returns in EAX (AL)
  1322                              <1> 	;	AL = 0 & CF=1 -> longname not found
  1323                              <1> 	;	     the file/directory has no longname
  1324                              <1> 	; 	cf = 0 -> AL = FAT Type 
  1325                              <1>  
  1326                              <1> 	; 17/10/2009
  1327                              <1> 	; ASCIIZ string will be returned
  1328                              <1> 	; as LongFileName
  1329                              <1> 	; clearing/reset is not needed
  1330                              <1> 	;mov	ecx, 33
  1331                              <1> 	;mov	edi, LongFileName
  1332                              <1> 	;sub	ax, ax ; 0
  1333                              <1> 	;rep	stosw
  1334                              <1> 
  1335                              <1> 	;mov	byte [LongNameFound], 0
  1336                              <1> 
  1337                              <1> 	; ESI = ASCIIZ file/directory name address
  1338                              <1> 	;   AL = Attributes AND mask 
  1339                              <1> 	;	(Result of AND must be equal to AL)
  1340                              <1> 	;   AH = Negative attributes mask 
  1341                              <1> 	;	(Result of AND must be ZERO)
  1342 0000AD99 66B80008            <1> 	mov	ax, 0800h 
  1343                              <1> 		; it must not be volume name or longname
  1344 0000AD9D E87DDDFFFF          <1> 	call	find_first_file
  1345 0000ADA2 7216                <1> 	jc	short loc_fln_retn
  1346                              <1>  
  1347                              <1> loc_fln_check_FAT_Type:
  1348 0000ADA4 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
  1349 0000ADAB 7306                <1> 	jnb	short loc_fln_check_longname_yes_sign
  1350                              <1> 
  1351 0000ADAD E839000000          <1> 	call	get_fs_longname
  1352 0000ADB2 C3                  <1> 	retn
  1353                              <1> 
  1354                              <1> loc_fln_check_longname_yes_sign:
  1355 0000ADB3 08FF                <1> 	or	bh, bh
  1356 0000ADB5 7504                <1> 	jnz	short loc_fln_check_longnamefound_number
  1357                              <1> loc_fln_longname_not_found_retn:
  1358 0000ADB7 31C0                <1> 	xor	eax, eax 
  1359                              <1> 	; cf = 1 & al = 0 -> longname not found
  1360 0000ADB9 F9                  <1> 	stc
  1361                              <1> loc_fln_retn:
  1362 0000ADBA C3                  <1> 	retn
  1363                              <1> 
  1364                              <1> loc_fln_check_longnamefound_number:
  1365                              <1> 	; 'LongNameFound' is set by
  1366                              <1>         ; by 'save_longname_sub_component'
  1367                              <1> 	; which is called from
  1368                              <1> 	; 'find_directory_entry' 
  1369                              <1> 	; which is called from 
  1370                              <1> 	; 'find_first_file'
  1371                              <1> 	; It must 1 if the longname is valid
  1372 0000ADBB 803D[41670100]01    <1>         cmp     byte [LongNameFound], 1
  1373 0000ADC2 75F3                <1> 	jne	short loc_fln_longname_not_found_retn
  1374                              <1>              
  1375                              <1> loc_fln_calculate_checksum: 
  1376 0000ADC4 E813000000          <1> 	call	calculate_checksum
  1377                              <1> 	; AL = shortname checksum
  1378                              <1> 
  1379                              <1> loc_fln_longname_validation:
  1380                              <1> 	; 'LFN_CheckSum' has been set already
  1381                              <1> 	; by 'save_longname_sub_component'
  1382                              <1> 	; which is called from
  1383                              <1> 	; 'find_directory_entry' 
  1384                              <1> 	; which is called from 
  1385                              <1> 	; 'find_first_file'
  1386 0000ADC9 3805[43670100]      <1> 	cmp	[LFN_CheckSum], al
  1387 0000ADCF 75E6                <1> 	jne	short loc_fln_longname_not_found_retn
  1388                              <1> 
  1389 0000ADD1 BE[44670100]        <1> 	mov	esi, LongFileName
  1390 0000ADD6 A0[455F0100]        <1> 	mov	al, [Current_FATType]
  1391 0000ADDB C3                  <1> 	retn
  1392                              <1> 
  1393                              <1> calculate_checksum:
  1394                              <1> 	; 13/02/2016 (TRDOS 386 = TRDOS v2.0)
  1395                              <1> 	; 17/10/2009 (DIR.ASM, 'proc_calculate_checksum')
  1396                              <1>         ;    
  1397                              <1> 	; INPUT ->
  1398                              <1> 	;	ESI = 11 byte DOS File Name location
  1399                              <1> 	;	(in DOS Directory Entry Format)
  1400                              <1> 	; OUTPUT ->
  1401                              <1> 	;	 AL = 8 bit checksum (CRC) value
  1402                              <1> 	;
  1403                              <1> 	; (Modified registers: EAX, ECX, ESI)
  1404                              <1> 
  1405                              <1> 	; Erdogan Tan [ 17-10-2009 ]
  1406                              <1> 	;  'ror al, 1' instruction
  1407                              <1> 
  1408                              <1> 	; Erdogan Tan [ 20-06-2004 ]
  1409                              <1> 	; This 8086 assembly code is an original code
  1410                              <1> 	; which is adapted from C code in
  1411                              <1> 	; Microsoft FAT32 File System Specification
  1412                              <1> 	; Version 1.03, December 6, 2000
  1413                              <1> 	; Page 28
  1414                              <1> 
  1415 0000ADDC 30C0                <1> 	xor	al, al
  1416 0000ADDE B90B000000          <1> 	mov	ecx, 11
  1417                              <1> loc_next_sum:
  1418                              <1> 	;xor	ah, ah
  1419                              <1> 	;test	al, 1
  1420                              <1> 	;jz	short pass_ah_80h
  1421                              <1> 	;mov	ah, 80h
  1422                              <1> ;pass_ah_80h:
  1423                              <1> 	;shr	al, 1
  1424 0000ADE3 D0C8                <1> 	ror	al, 1 ; 17/10/2009  
  1425 0000ADE5 0206                <1> 	add	al, [esi]
  1426 0000ADE7 46                  <1> 	inc	esi
  1427                              <1> 	;add	al, ah
  1428 0000ADE8 E2F9                <1> 	loop	loc_next_sum
  1429 0000ADEA C3                  <1> 	retn
  1430                              <1> 
  1431                              <1> get_fs_longname:
  1432                              <1> 	; temporary (13/02/2016)
  1433 0000ADEB 31C0                <1> 	xor eax, eax
  1434 0000ADED F9                  <1> 	stc
  1435 0000ADEE C3                  <1> 	retn
  1436                              <1> 
  1437                              <1> make_sub_directory:
  1438                              <1> 	; 16/10/2016
  1439                              <1> 	; 02/03/2016, 03/03/2016
  1440                              <1> 	; 26/02/2016, 27/02/2016
  1441                              <1> 	; 21/02/2016 (TRDOS 386 = TRDOS v2.0)
  1442                              <1> 	; 01/08/2011 (DIR.ASM, 'proc_make_directory')
  1443                              <1> 	; 10/07/2010
  1444                              <1> 	; INPUT ->
  1445                              <1> 	; 	ESI = ASCIIZ Directory Name
  1446                              <1> 	;	CL = Directory Attributes
  1447                              <1> 	; OUTPUT ->
  1448                              <1> 	;	EAX = New sub dir's first cluster
  1449                              <1> 	;	ESI = Logical Dos Drv Descr. Table Addr.
  1450                              <1> 	;	CF = 1 -> error code in AL (EAX)
  1451                              <1> 
  1452                              <1> 	;test	cl, 10h  ; directory
  1453                              <1> 	;jz	short loc_make_directory_access_denied
  1454                              <1> 	;test	cl, 08h ; volume name
  1455                              <1> 	;jnz	short loc_make_directory_access_denied
  1456                              <1> 
  1457 0000ADEF 80E107              <1> 	and	cl, 07h
  1458 0000ADF2 880D[C0680100]      <1> 	mov	byte [mkdir_attrib], cl
  1459                              <1> 
  1460 0000ADF8 56                  <1> 	push	esi
  1461 0000ADF9 31DB                <1> 	xor	ebx, ebx
  1462 0000ADFB 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  1463 0000AE01 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  1464 0000AE06 01DE                <1> 	add	esi, ebx
  1465 0000AE08 5B                  <1> 	pop	ebx
  1466                              <1> 
  1467                              <1> 	; 10/07/2010 -> 1st writable disk check for trdos
  1468                              <1> 	; LD_DiskType = 0 for write protection (read only) 
  1469 0000AE09 807E0101            <1> 	cmp	byte [esi+LD_DiskType], 1 ; 0 = Invalid
  1470 0000AE0D 730B                <1> 	jnb	short loc_mkdir_check_file_sytem
  1471                              <1> 	; 16/10/2016 (13h -> 30)
  1472 0000AE0F B81E000000          <1> 	mov	eax, 30 ; 'Disk write-protected' error
  1473 0000AE14 BA00000000          <1> 	mov	edx, 0
  1474                              <1> 	; err retn: EDX = 0, EBX = Dir name offset
  1475                              <1> 	;ESI = Logical DOS drive description table address
  1476 0000AE19 C3                  <1> 	retn
  1477                              <1> 
  1478                              <1> ;loc_make_directory_access_denied:
  1479                              <1> 	;mov	ax, 05h ; access denied (invalid attributes input)
  1480                              <1> 	;stc
  1481                              <1> 	;retn
  1482                              <1> 
  1483                              <1> loc_mkdir_check_file_sytem:
  1484 0000AE1A 807E0301            <1> 	cmp	byte [esi+LD_FATType], 1
  1485 0000AE1E 730B                <1> 	jnb	short loc_mkdir_check_free_sectors
  1486                              <1> 
  1487                              <1> loc_make_fs_directory:
  1488 0000AE20 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
  1489                              <1> 	; EAX = Parent directory DDT Address
  1490                              <1> 	; ESI = Logical DOS Drive DT Address
  1491                              <1> 	; EBX = Directory name offset (as ASCIIZ name)
  1492 0000AE25 E8D5150000          <1> 	call	make_fs_directory
  1493 0000AE2A C3                  <1> 	retn
  1494                              <1> 
  1495                              <1> loc_mkdir_check_free_sectors:
  1496 0000AE2B 0FB64613            <1>         movzx   eax, byte [esi+LD_BPB+SecPerClust]
  1497 0000AE2F 8B4E74              <1> 	mov	ecx, [esi+LD_FreeSectors]
  1498 0000AE32 39C1                <1> 	cmp	ecx, eax
  1499 0000AE34 7255                <1> 	jb	short loc_mkdir_insufficient_disk_space
  1500                              <1> 
  1501                              <1> loc_make_fat_directory:
  1502 0000AE36 891D[B0680100]      <1> 	mov	[mkdir_DirName_Offset], ebx
  1503 0000AE3C 890D[BC680100]      <1> 	mov	[mkdir_FreeSectors], ecx
  1504                              <1> 
  1505                              <1> 	;mov	al, [esi+LD_BPB+SecPerClust]
  1506 0000AE42 A2[C2680100]        <1> 	mov	byte [mkdir_SecPerClust], al
  1507                              <1> 
  1508                              <1> loc_mkdir_gffc_1:
  1509 0000AE47 E80F180000          <1> 	call	get_first_free_cluster
  1510 0000AE4C 722A                <1> 	jc	short loc_mkdir_gffc_retn
  1511                              <1> 
  1512                              <1> ;loc_mkdir_gffc_1_cont: 
  1513                              <1> 	;cmp	eax, 2
  1514                              <1> 	;jb	short loc_mkdir_gffc_insufficient_disk_space
  1515                              <1> 
  1516                              <1> ;loc_mkdir_gffc_1_save_fcluster:  
  1517 0000AE4E A3[B4680100]        <1> 	mov	[mkdir_FFCluster], eax
  1518                              <1> 
  1519                              <1> loc_mkdir_locate_ffe:
  1520                              <1> 	; Current directory fcluster <> Directory buffer cluster
  1521                              <1> 	; Current directory will be reloaded by
  1522                              <1> 	; 'locate_current_dir_file' procedure
  1523                              <1> 	;
  1524                              <1> 	; ESI = Logical DOS Drive Description Table Address 
  1525                              <1> 	;push	esi ; 27/02/2016
  1526 0000AE53 31C0                <1> 	xor	eax, eax
  1527 0000AE55 89C1                <1>         mov	ecx, eax
  1528 0000AE57 6649                <1> 	dec	cx ; FFFFh  
  1529                              <1> 	; CX = FFFFh -> find first deleted or free entry
  1530                              <1> 	; ESI would be ASCIIZ filename address if the call
  1531                              <1> 	; would not be for first free or deleted dir entry
  1532 0000AE59 E8D0FAFFFF          <1> 	call	locate_current_dir_file
  1533 0000AE5E 734C                <1> 	jnc	short loc_mkdir_set_ff_dir_entry_1
  1534                              <1> 	;pop	esi 
  1535                              <1> 	; ESI = Logical DOS Drive Description Table Address 
  1536 0000AE60 83F802              <1> 	cmp	eax, 2  ; cmp al, 2 ; File/Dir not found !
  1537 0000AE63 752B                <1> 	jne	short loc_mkdir_stc_return
  1538                              <1> 
  1539                              <1> loc_mkdir_add_new_cluster:
  1540 0000AE65 3805[455F0100]      <1> 	cmp	byte [Current_FATType], al ; 2
  1541                              <1> 	;cmp	byte ptr [esi+LD_FATType], 2
  1542 0000AE6B 770C                <1> 	ja	short loc_mkdir_add_new_cluster_check_fsc
  1543 0000AE6D 803D[445F0100]01    <1> 	cmp	byte [Current_Dir_Level], 1
  1544                              <1> 	;cmp	byte [esi+LD_CDirLevel], 1
  1545 0000AE74 7303                <1> 	jnb	short loc_mkdir_add_new_cluster_check_fsc
  1546                              <1> 
  1547 0000AE76 B00C                <1> 	mov	al, 12 ; No more files 
  1548                              <1> loc_mkdir_gffc_retn:
  1549 0000AE78 C3                  <1> 	retn
  1550                              <1> 
  1551                              <1> loc_mkdir_add_new_cluster_check_fsc:
  1552 0000AE79 8B0D[BC680100]      <1> 	mov	ecx, [mkdir_FreeSectors]
  1553                              <1> 	;movzx	eax, byte [mkdir_SecPerClust]
  1554 0000AE7F A0[C2680100]        <1> 	mov	al, [mkdir_SecPerClust]
  1555 0000AE84 66D1E0              <1> 	shl	ax, 1 ; AX = 2 * AX
  1556 0000AE87 39C1                <1> 	cmp	ecx, eax
  1557 0000AE89 7350                <1> 	jnb	short loc_mkdir_add_new_subdir_cluster
  1558                              <1> 
  1559                              <1> loc_mkdir_insufficient_disk_space:
  1560                              <1> 	;mov	edx, ecx
  1561                              <1> ;loc_mkdir_gffc_insufficient_disk_space:
  1562 0000AE8B 66B82700            <1> 	mov	ax, 27h ; MSDOS err => insufficient disk space
  1563                              <1> 	; err retn: EDX = Free sectors, EBX = Dir name offset
  1564                              <1>         ; ESI -> Dos drive description table address
  1565                              <1> 	;; ecx = edx
  1566                              <1> 	;
  1567 0000AE8F C3                  <1> 	retn
  1568                              <1> 
  1569                              <1> loc_mkdir_stc_return:
  1570 0000AE90 F9                  <1> 	stc
  1571 0000AE91 C3                  <1> 	retn 
  1572                              <1> 
  1573                              <1> loc_mkdir_gffc_2:
  1574 0000AE92 E8C4170000          <1> 	call	get_first_free_cluster
  1575 0000AE97 72DF                <1> 	jc	short loc_mkdir_gffc_retn
  1576                              <1> 
  1577                              <1> ;loc_mkdir_gffc_1_cont: 
  1578                              <1> 	;cmp	eax, 2
  1579                              <1> 	;jb	short loc_mkdir_gffc_insufficient_disk_space
  1580                              <1> 
  1581                              <1> ;loc_mkdir_gffc_2_save_fcluster:  
  1582 0000AE99 A3[B4680100]        <1> 	mov	[mkdir_FFCluster], eax
  1583                              <1> 
  1584 0000AE9E A1[B8680100]        <1> 	mov	eax, [mkdir_LastDirCluster]
  1585                              <1> 
  1586 0000AEA3 E842170000          <1> 	call	load_FAT_sub_directory 
  1587 0000AEA8 72CE                <1> 	jc	short loc_mkdir_gffc_retn
  1588                              <1> 
  1589 0000AEAA 31FF                <1> 	xor	edi, edi
  1590                              <1> loc_mkdir_set_ff_dir_entry_1:
  1591                              <1> 	; 27/02/2016
  1592 0000AEAC 56                  <1> 	push	esi ; Logical DOS Drv Desc. Tbl. address
  1593                              <1> 	; EDI = Directory Entry Address
  1594 0000AEAD 8B35[B0680100]      <1> 	mov	esi, [mkdir_DirName_Offset]
  1595 0000AEB3 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1596                              <1> 
  1597 0000AEB8 66B91000            <1> 	mov	cx, 10h	; CL = Directory attribute
  1598                              <1> 			; CH = 0 -> File size is 0
  1599 0000AEBC 0A0D[C0680100]      <1> 	or	cl, [mkdir_attrib] ; S, H, R  
  1600 0000AEC2 E8B0010000          <1> 	call	make_directory_entry
  1601                              <1> 
  1602 0000AEC7 5E                  <1> 	pop	esi
  1603                              <1> 
  1604 0000AEC8 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  1605 0000AECF E880020000          <1> 	call	save_directory_buffer
  1606 0000AED4 0F83DA000000        <1>         jnc     loc_mkdir_set_ff_dir_entry_2
  1607                              <1> 
  1608                              <1> loc_mkdir_return:
  1609 0000AEDA C3                  <1> 	retn
  1610                              <1> 
  1611                              <1> loc_mkdir_add_new_subdir_cluster:
  1612 0000AEDB 8B15[71660100]      <1> 	mov	edx, [DirBuff_Cluster]
  1613 0000AEE1 8915[B8680100]      <1> 	mov	[mkdir_LastDirCluster], edx       
  1614                              <1> 
  1615 0000AEE7 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1616 0000AEEC E8F9160000          <1> 	call	load_FAT_sub_directory 
  1617 0000AEF1 72E7                <1> 	jc	short loc_mkdir_return
  1618                              <1> 	; eax = 0
  1619                              <1> 	; ecx =  directory buffer sector count (<= 128)
  1620                              <1> 
  1621                              <1> pass_mkdir_add_new_subdir_cluster:
  1622 0000AEF3 29FF                <1> 	sub	edi, edi ; 0
  1623                              <1> 	;mov	al, 128 ; double word
  1624                              <1> 	;mul	ecx ; ecx =  directory buffer sector count
  1625                              <1> 	;mov	ecx, eax
  1626                              <1> 	;shl	cx, 7 ; 128 * sector count	
  1627 0000AEF5 668B4611            <1> 	mov	ax, [esi+LD_BPB+BytesPerSec] ; 512
  1628 0000AEF9 66C1E802            <1> 	shr	ax, 2 ; 'byte count / 4' for 'stosd'
  1629 0000AEFD 66F7E1              <1> 	mul	cx ; max = 128*(512/4) -> 16384 (stosd)
  1630 0000AF00 6689C1              <1> 	mov	cx, ax
  1631 0000AF03 6629C0              <1> 	sub	ax, ax ; 0
  1632 0000AF06 F3AB                <1> 	rep	stosd ; clear directory buffer
  1633                              <1> 
  1634 0000AF08 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  1635 0000AF0F E840020000          <1> 	call	save_directory_buffer 
  1636 0000AF14 72C4                <1> 	jc	short loc_mkdir_return
  1637                              <1> 
  1638                              <1> loc_mkdir_save_added_cluster:
  1639 0000AF16 A1[B8680100]        <1> 	mov	eax, [mkdir_LastDirCluster]
  1640 0000AF1B 8B0D[B4680100]      <1> 	mov	ecx, [mkdir_FFCluster]
  1641                              <1> 	; 01/03/2016
  1642 0000AF21 31D2                <1> 	xor	edx, edx
  1643 0000AF23 8915[62660100]      <1> 	mov	[FAT_ClusterCounter], edx ; 0 ; reset
  1644 0000AF29 E800180000          <1> 	call	update_cluster
  1645 0000AF2E 7304                <1> 	jnc	short loc_mkdir_save_fat_buffer_0
  1646 0000AF30 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  1647 0000AF32 7518                <1> 	jnz	short loc_mkdir_save_fat_buffer_stc_retn
  1648                              <1> 
  1649                              <1> loc_mkdir_save_fat_buffer_0:
  1650 0000AF34 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1651 0000AF39 A3[B8680100]        <1> 	mov	[mkdir_LastDirCluster], eax
  1652                              <1> 
  1653 0000AF3E 31C9                <1> 	xor	ecx, ecx
  1654 0000AF40 49                  <1> 	dec	ecx ; FFFFFFFFh
  1655                              <1> 	; ESI = Logical DOS Drive Description Table address 
  1656 0000AF41 E8E8170000          <1> 	call	update_cluster
  1657 0000AF46 731A                <1> 	jnc	short loc_mkdir_save_fat_buffer_1
  1658 0000AF48 09C0                <1> 	or	eax, eax
  1659 0000AF4A 7416                <1> 	jz	short loc_mkdir_save_fat_buffer_1
  1660                              <1> 
  1661                              <1> loc_mkdir_save_fat_buffer_stc_retn:
  1662                              <1> 	; 01/03/2016
  1663 0000AF4C 803D[62660100]01    <1> 	cmp	byte [FAT_ClusterCounter], 1
  1664 0000AF53 720C                <1> 	jb	short loc_mkdir_save_fat_buffer_retn
  1665                              <1> 
  1666 0000AF55 66BB00FF            <1> 	mov	bx, 0FF00h ; recalculate free space (BL = 0)
  1667                              <1> 			   ; (BH = FFh -> Use ESI as Drv Param. Tbl.)
  1668 0000AF59 50                  <1> 	push	eax
  1669 0000AF5A E8211B0000          <1> 	call	calculate_fat_freespace
  1670 0000AF5F 58                  <1> 	pop	eax
  1671 0000AF60 F9                  <1> 	stc
  1672                              <1> loc_mkdir_save_fat_buffer_retn:
  1673 0000AF61 C3                  <1> 	retn
  1674                              <1> 
  1675                              <1> loc_mkdir_save_fat_buffer_1:
  1676                              <1> 	; byte [FAT_BuffValidData] = 2 
  1677 0000AF62 E8841A0000          <1> 	call	save_fat_buffer
  1678 0000AF67 72E3                <1> 	jc	short loc_mkdir_save_fat_buffer_stc_retn
  1679                              <1> 
  1680                              <1> 	; 01/03/2016
  1681 0000AF69 803D[62660100]01    <1> 	cmp	byte [FAT_ClusterCounter], 1
  1682 0000AF70 721B                <1> 	jb	short loc_mkdir_save_fat_buffer_2
  1683                              <1> 
  1684                              <1> 	; ESI = Logical DOS Drive Description Table address 
  1685 0000AF72 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  1686 0000AF77 66BB01FF            <1> 	mov	bx, 0FF01h ; add free clusters 
  1687 0000AF7B E8001B0000          <1> 	call	calculate_fat_freespace
  1688                              <1> 
  1689                              <1> 	;inc	eax ; 0FFFFFFFFh -> 0 ; recalculation is needed!
  1690                              <1> 	;jnz	short loc_mkdir_save_fat_buffer_2
  1691                              <1> 
  1692                              <1> 	; ecx > 0 -> Recalculation is needed
  1693 0000AF80 09C9                <1> 	or	ecx, ecx 
  1694 0000AF82 7409                <1> 	jz	short loc_mkdir_save_fat_buffer_2
  1695                              <1> 
  1696 0000AF84 66BB00FF            <1> 	mov	bx, 0FF00h ; ; recalculate free space
  1697 0000AF88 E8F31A0000          <1> 	call	calculate_fat_freespace
  1698                              <1> 
  1699                              <1> loc_mkdir_save_fat_buffer_2:
  1700 0000AF8D C605[C3680100]01    <1> 	mov	byte [mkdir_add_new_cluster], 1
  1701 0000AF94 E9C4000000          <1> 	jmp	loc_mkdir_upd_parent_dir_lmdt
  1702                              <1> 
  1703                              <1> loc_mkdir_update_sub_dir_cluster:
  1704 0000AF99 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1705 0000AF9E 29C9                <1> 	sub	ecx, ecx ; 0
  1706                              <1> 	; 01/03/2016
  1707 0000AFA0 890D[62660100]      <1> 	mov	[FAT_ClusterCounter], ecx ; 0 ; Reset
  1708 0000AFA6 49                  <1> 	dec	ecx ; 0FFFFFFFFh
  1709                              <1> 
  1710                              <1> 	; ESI = Logical DOS Drive Descisption Table address  
  1711 0000AFA7 E882170000          <1> 	call	update_cluster
  1712 0000AFAC 7379                <1> 	jnc	short loc_mkdir_save_fat_buffer_3
  1713 0000AFAE 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  1714 0000AFB0 7475                <1> 	jz	short loc_mkdir_save_fat_buffer_3
  1715                              <1> 	; 01/03/2016
  1716 0000AFB2 EB98                <1> 	jmp	short loc_mkdir_save_fat_buffer_stc_retn
  1717                              <1> 
  1718                              <1> loc_mkdir_set_ff_dir_entry_2:
  1719                              <1> 	; ESI = Logical DOS Drive Description Table address  
  1720 0000AFB4 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1721                              <1> 	; Load disk sectors as a directory cluster
  1722 0000AFB9 E82C160000          <1> 	call	load_FAT_sub_directory 
  1723 0000AFBE 7266                <1> 	jc	short retn_make_fat_directory
  1724                              <1> 	
  1725                              <1> 	; eax = 0
  1726                              <1> 	; ecx =  directory buffer sector count (<= 128)
  1727                              <1> 
  1728 0000AFC0 BF40000800          <1> 	mov	edi, Directory_Buffer + 64 ; 26/02/2016
  1729                              <1> 
  1730                              <1> 	; 02/03/2016
  1731 0000AFC5 668B4611            <1> 	mov	ax, [esi+LD_BPB+BytesPerSec] ; 512
  1732 0000AFC9 66C1E802            <1> 	shr	ax, 2 ; 'byte count / 4' for 'stosd'
  1733 0000AFCD F7E1                <1> 	mul 	ecx
  1734 0000AFCF 89C1                <1> 	mov	ecx, eax
  1735 0000AFD1 6629C0              <1> 	sub	ax, ax
  1736 0000AFD4 F3AB                <1> 	rep	stosd
  1737                              <1> 
  1738                              <1> 	;;mov	al, 128 ; double word
  1739                              <1> 	;;mul	ecx ; ecx =  directory buffer sector count
  1740                              <1> 	;;mov	ecx, eax
  1741                              <1> 	;shl	cx, 7 ; 128 * sector count	
  1742                              <1> 	;;sub	eax, eax
  1743                              <1> 	;;sub	al, al ; 0
  1744                              <1> 	;rep	stosd ; clear directory buffer
  1745                              <1> 
  1746 0000AFD6 BF00000800          <1> 	mov	edi, Directory_Buffer ; 26/02/2016
  1747                              <1> 	
  1748 0000AFDB 56                  <1> 	push	esi
  1749                              <1> 
  1750 0000AFDC BE[C4680100]        <1> 	mov	esi, mkdir_Name
  1751 0000AFE1 66C7062E00          <1> 	mov	word [esi], 2Eh ; db '.', '0'
  1752                              <1> 
  1753 0000AFE6 A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1754 0000AFEB 66B91000            <1> 	mov	cx, 10h ; CL = Directory attribute
  1755                              <1> 			; CH = 0 -> File size is 0
  1756 0000AFEF E883000000          <1> 	call	make_directory_entry
  1757                              <1> 
  1758 0000AFF4 BF20000800          <1> 	mov	edi, Directory_Buffer + 32 ; 26/02/2016
  1759                              <1> 
  1760                              <1> 	; 03/03/2016
  1761                              <1> 	; Following modification has been done according to 
  1762                              <1> 	; 'Microsoft Extensible Firmware Initiative
  1763                              <1> 	; FAT32 File System Specification' document,
  1764                              <1> 	; 'FAT: General Overview of On-Disk FormatPage 25'.
  1765                              <1> 	; "Finally, you set DIR_FstClusLO and DIR_FstClusHI
  1766                              <1> 	; for the dotdot entry (the second entry) to the
  1767                              <1> 	; first cluster number of the directory in which you 
  1768                              <1> 	; just created the directory (value is 0 if this directory
  1769                              <1> 	; is the root directory even for FAT32 volumes)."
  1770                              <1> 	; (Correctness of this modification has been verified
  1771                              <1> 	;  by using Windows 98 'scandisk.exe'.)
  1772                              <1> 
  1773 0000AFF9 29C0                <1> 	sub	eax, eax
  1774 0000AFFB 3805[445F0100]      <1> 	cmp	byte [Current_Dir_Level], al ; 0
  1775 0000B001 7605                <1> 	jna	short loc_mkdir_set_ff_dir_entry_3
  1776 0000B003 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster] ; parent dir
  1777                              <1> loc_mkdir_set_ff_dir_entry_3:
  1778 0000B008 66C746012E00        <1> 	mov	word [esi+1], 2Eh ; db '.', '0'
  1779                              <1> 
  1780                              <1> 	;mov	cx, 10h
  1781 0000B00E E864000000          <1> 	call	make_directory_entry
  1782                              <1> 
  1783 0000B013 5E                  <1> 	pop	esi
  1784                              <1> 
  1785 0000B014 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  1786 0000B01B E834010000          <1> 	call	save_directory_buffer
  1787 0000B020 0F8373FFFFFF        <1>         jnc     loc_mkdir_update_sub_dir_cluster
  1788                              <1>  
  1789                              <1> retn_make_fat_directory:
  1790 0000B026 C3                  <1> 	retn
  1791                              <1> 
  1792                              <1> loc_mkdir_save_fat_buffer_3:
  1793                              <1> 	; 01/03/2016
  1794                              <1> 	; byte [FAT_BuffValidData] = 2 
  1795 0000B027 E8BF190000          <1> 	call	save_fat_buffer
  1796 0000B02C 0F821AFFFFFF        <1>         jc      loc_mkdir_save_fat_buffer_stc_retn
  1797                              <1> 
  1798 0000B032 803D[62660100]01    <1> 	cmp	byte [FAT_ClusterCounter], 1
  1799 0000B039 721B                <1> 	jb	short loc_mkdir_save_fat_buffer_4
  1800                              <1> 
  1801                              <1> 	; ESI = Logical DOS Drive Description Table address 
  1802 0000B03B A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  1803 0000B040 66BB01FF            <1> 	mov	bx, 0FF01h ; add free clusters 
  1804 0000B044 E8371A0000          <1> 	call	calculate_fat_freespace
  1805                              <1> 
  1806                              <1> 	;inc	eax ; 0FFFFFFFFh -> 0 ; recalculation is needed!
  1807                              <1>         ;jnz    short loc_mkdir_save_fat_buffer_4
  1808                              <1> 
  1809                              <1> 	; ecx > 0 -> Recalculation is needed
  1810 0000B049 09C9                <1> 	or	ecx, ecx 
  1811 0000B04B 7409                <1>         jz      short loc_mkdir_save_fat_buffer_4
  1812                              <1> 
  1813 0000B04D 66BB00FF            <1> 	mov	bx, 0FF00h ; recalculate free space
  1814 0000B051 E82A1A0000          <1> 	call	calculate_fat_freespace
  1815                              <1> 
  1816                              <1> loc_mkdir_save_fat_buffer_4:	
  1817 0000B056 C605[C3680100]00    <1> 	mov	byte [mkdir_add_new_cluster], 0
  1818                              <1> 
  1819                              <1> loc_mkdir_upd_parent_dir_lmdt:
  1820 0000B05D E88D010000          <1> 	call	update_parent_dir_lmdt
  1821                              <1> 
  1822                              <1> 	; 01/03/2016
  1823 0000B062 803D[C3680100]00    <1> 	cmp	byte [mkdir_add_new_cluster], 0
  1824 0000B069 0F8723FEFFFF        <1>         ja      loc_mkdir_gffc_2
  1825                              <1> 
  1826                              <1> loc_mkdir_retn_new_dir_cluster:
  1827 0000B06F A1[B4680100]        <1> 	mov	eax, [mkdir_FFCluster]
  1828 0000B074 31D2                <1> 	xor	edx, edx
  1829                              <1> loc_mkdir_retn:
  1830 0000B076 C3                  <1> 	retn
  1831                              <1> 
  1832                              <1> make_directory_entry:
  1833                              <1> 	; 02/03/2016
  1834                              <1> 	; 21/02/2016 (TRDOS 386 = TRDOS v2.0)
  1835                              <1> 	; 09/08/2010 (DIR.ASM, 'proc_make_directory_entry')
  1836                              <1> 	; 17/07/2010
  1837                              <1> 	; INPUT ->
  1838                              <1> 	; 	EDI = Directory Entry Address
  1839                              <1> 	;	ESI = Dot File Name Location
  1840                              <1> 	;	EAX = First Cluster
  1841                              <1> 	;	File Size = 0 (Must be set later)
  1842                              <1> 	;	CL = Attributes
  1843                              <1> 	;	CH = 0 (File size = 0) 
  1844                              <1> 	;	(If CH>0, File size is in dword [EBX]) (*)
  1845                              <1> 	; OUTPUT -> 
  1846                              <1> 	;	EDI = Directory Entry Address
  1847                              <1> 	;	ESI = Dot File Name Location (Capitalized)
  1848                              <1> 	;	If CH input = 0, File Size = 0
  1849                              <1> 	;	Otherwise file size is as dword [EBX] (*)
  1850                              <1> 	;	DX = Date, AX = Time in DOS Dir Entry format
  1851                              <1> 	;	EBX = same
  1852                              <1> 	;	ECX = same
  1853                              <1> 
  1854 0000B077 51                  <1> 	push	ecx
  1855                              <1> 
  1856 0000B078 884F0B              <1> 	mov	[edi+11], cl ; Attributes
  1857 0000B07B 6689471A            <1> 	mov	[edi+26], ax ; FClusterLw, 26
  1858 0000B07F C1E810              <1> 	shr	eax, 16
  1859 0000B082 66894714            <1> 	mov	[edi+20], ax ; FClusterHw, 20
  1860 0000B086 6631C0              <1> 	xor	ax, ax 
  1861 0000B089 6689470C            <1> 	mov	[edi+12], ax ; NTReserved, 12
  1862                              <1> 			     ; CrtTimeTenth, 13
  1863 0000B08D 08ED                <1> 	or	ch, ch
  1864 0000B08F 7402                <1> 	jz	short loc_make_direntry_set_filesize
  1865                              <1> 
  1866 0000B091 8B03                <1> 	mov	eax, [ebx]
  1867                              <1>         
  1868                              <1> loc_make_direntry_set_filesize:
  1869 0000B093 89471C              <1> 	mov	[edi+28], eax ; FileSize, 28
  1870                              <1> 	
  1871 0000B096 E88AFBFFFF          <1> 	call	convert_file_name
  1872                              <1> 	;EDI = Dir Entry Format File Name Location
  1873                              <1> 	;ESI = Dot File Name Location (capitalized)
  1874                              <1> 
  1875 0000B09B E816000000          <1> 	call	convert_current_date_time
  1876                              <1> 	; OUTPUT -> DX = Date in dos dir entry format
  1877                              <1>         ; 	    AX = Time in dos dir entry format
  1878 0000B0A0 6689470E            <1> 	mov	[edi+14], ax ; CrtTime, 14
  1879 0000B0A4 66895710            <1> 	mov	[edi+16], dx ; CrtDate, 16
  1880 0000B0A8 66895712            <1> 	mov	[edi+18], dx ; LastAccDate, 18
  1881 0000B0AC 66894716            <1> 	mov	[edi+22], ax ; WrtTime, 14
  1882 0000B0B0 66895718            <1> 	mov	[edi+24], dx ; WrtDate, 16
  1883 0000B0B4 59                  <1> 	pop	ecx
  1884                              <1> 
  1885 0000B0B5 C3                  <1> 	retn
  1886                              <1> 
  1887                              <1> convert_current_date_time:
  1888                              <1> 	; 21/02/2016 (TRDOS 386 = TRDOS v2.0)
  1889                              <1> 	; 13/06/2010 (DIR.ASM, 'proc_convert_current_date_time')
  1890                              <1> 	; converts date&time to dos dir entry format
  1891                              <1> 	; INPUT -> none
  1892                              <1> 	; OUTPUT -> DX = Date in dos dir entry format
  1893                              <1> 	;           AX = Time in dos dir entry format
  1894                              <1>  
  1895 0000B0B6 B404                <1> 	mov	ah, 04h ; Return Current Date
  1896 0000B0B8 E828B0FFFF          <1> 	call	int1Ah 
  1897                              <1> 
  1898 0000B0BD 88E8                <1> 	mov	al, ch ; <- century BCD
  1899 0000B0BF 240F                <1> 	and	al, 0Fh
  1900 0000B0C1 88EC                <1> 	mov	ah, ch
  1901 0000B0C3 C0EC04              <1> 	shr	ah, 4
  1902 0000B0C6 D50A                <1> 	aad
  1903 0000B0C8 88C5                <1> 	mov	ch, al ; -> century 
  1904                              <1> 
  1905 0000B0CA 88C8                <1> 	mov	al, cl ; <- year BCD
  1906 0000B0CC 240F                <1> 	and	al, 0Fh
  1907 0000B0CE 88CC                <1> 	mov	ah, cl
  1908 0000B0D0 C0EC04              <1> 	shr	ah, 4
  1909 0000B0D3 D50A                <1> 	aad
  1910 0000B0D5 88C1                <1> 	mov	cl, al ; -> year
  1911                              <1> 
  1912 0000B0D7 88E8                <1> 	mov	al, ch
  1913 0000B0D9 B464                <1> 	mov	ah, 100
  1914 0000B0DB F6E4                <1> 	mul	ah
  1915 0000B0DD 30ED                <1> 	xor	ch, ch
  1916 0000B0DF 6601C8              <1> 	add	ax, cx
  1917 0000B0E2 662DBC07            <1> 	sub	ax, 1980 ; ms-dos epoch
  1918 0000B0E6 6689C1              <1> 	mov	cx, ax
  1919                              <1> 
  1920 0000B0E9 88F0                <1> 	mov	al, dh ; <- month in bcd
  1921 0000B0EB 240F                <1> 	and	al, 0Fh
  1922 0000B0ED 88F4                <1> 	mov	ah, dh
  1923 0000B0EF C0EC04              <1> 	shr	ah, 4
  1924 0000B0F2 D50A                <1> 	aad
  1925 0000B0F4 88C6                <1> 	mov	dh, al ; -> month
  1926                              <1> 
  1927 0000B0F6 88D0                <1> 	mov	al, dl ; <- day BCD
  1928 0000B0F8 240F                <1> 	and	al, 0Fh
  1929 0000B0FA 88D4                <1> 	mov	ah, dl
  1930 0000B0FC C0EC04              <1> 	shr	ah, 4
  1931 0000B0FF D50A                <1> 	aad
  1932 0000B101 88C2                <1> 	mov	dl, al ; -> day
  1933                              <1> 
  1934 0000B103 88C8                <1> 	mov	al, cl ; count of years from 1980
  1935 0000B105 66C1E004            <1> 	shl	ax, 4
  1936 0000B109 08F0                <1> 	or	al, dh ; month of year, 1 to 12
  1937 0000B10B 66C1E005            <1> 	shl	ax, 5
  1938 0000B10F 08D0                <1> 	or	al, dl ; day of year, 1 to 31
  1939                              <1> 	
  1940 0000B111 6650                <1> 	push	ax ; push date
  1941                              <1> 
  1942 0000B113 B402                <1> 	mov	ah, 02h ; Return Current Time
  1943 0000B115 E8CBAFFFFF          <1> 	call	int1Ah
  1944                              <1> 
  1945 0000B11A 88E8                <1> 	mov	al, ch ; <- hours BCD
  1946 0000B11C 240F                <1> 	and	al, 0Fh
  1947 0000B11E 88EC                <1> 	mov	ah, ch
  1948 0000B120 C0EC04              <1> 	shr	ah, 4
  1949 0000B123 D50A                <1> 	aad
  1950 0000B125 88C5                <1> 	mov	ch, al ; -> hours
  1951                              <1> 
  1952 0000B127 88C8                <1> 	mov	al, cl ; <- minutes BCD
  1953 0000B129 240F                <1> 	and	al, 0Fh
  1954 0000B12B 88CC                <1> 	mov	ah, cl
  1955 0000B12D C0EC04              <1> 	shr	ah, 4
  1956 0000B130 D50A                <1> 	aad
  1957 0000B132 88C1                <1> 	mov	cl, al ; -> minutes
  1958                              <1> 
  1959 0000B134 88F0                <1> 	mov	al, dh ; <- seconds BCD
  1960 0000B136 240F                <1> 	and	al, 0Fh
  1961 0000B138 88F4                <1> 	mov	ah, dh
  1962 0000B13A C0EC04              <1> 	shr	ah, 4
  1963 0000B13D D50A                <1> 	aad
  1964 0000B13F 88C6                <1> 	mov	dh, al ; -> seconds
  1965                              <1> 
  1966 0000B141 88E8                <1> 	mov	al, ch ; hours
  1967 0000B143 66C1E006            <1> 	shl	ax, 6
  1968 0000B147 08C8                <1> 	or	al, cl ; minutes
  1969 0000B149 66C1E005            <1> 	shl	ax, 5
  1970 0000B14D D0EE                <1> 	shr	dh, 1 ; 2 seconds
  1971                              <1> 	; There is a bug in TRDOS v1 here !
  1972                              <1> 	; it was 'or al, dl' ! 
  1973 0000B14F 08F0                <1> 	or	al, dh ; seconds
  1974                              <1> 
  1975 0000B151 665A                <1> 	pop	dx ; pop date
  1976                              <1> 	
  1977 0000B153 C3                  <1> 	retn
  1978                              <1> 
  1979                              <1> save_directory_buffer:
  1980                              <1> 	; 15/10/2016
  1981                              <1> 	; 23/03/2016
  1982                              <1> 	; 26/02/2016
  1983                              <1> 	; 22/02/2016 (TRDOS 386 = TRDOS v2.0)
  1984                              <1> 	; 01/08/2011
  1985                              <1> 	; 14/03/2010
  1986                              <1> 	; INPUT ->
  1987                              <1> 	; 	 none
  1988                              <1> 	; OUTPUT ->
  1989                              <1> 	;  cf = 0 -> write OK...
  1990                              <1> 	;  cf = 1 -> error code in AL (EAX)
  1991                              <1> 	;  cf = 1 & AL = 0Dh => CH & CL = FS & FAT type
  1992                              <1> 	;  EBX = Directory Buffer Address
  1993                              <1> 	;
  1994                              <1> 	;  (EAX, ECX, EDX will be modified)
  1995                              <1>  
  1996 0000B154 BB00000800          <1> 	mov	ebx, Directory_Buffer
  1997 0000B159 803D[6C660100]02    <1> 	cmp	byte [DirBuff_ValidData], 2
  1998 0000B160 7403                <1> 	je	short loc_save_dir_buffer
  1999 0000B162 31C0                <1> 	xor	eax, eax
  2000 0000B164 C3                  <1> 	retn            
  2001                              <1> 
  2002                              <1> loc_save_dir_buffer:
  2003 0000B165 56                  <1> 	push	esi
  2004 0000B166 31DB                <1> 	xor	ebx, ebx 
  2005 0000B168 8A3D[6A660100]      <1>         mov     bh, [DirBuff_DRV]
  2006 0000B16E 80EF41              <1> 	sub	bh, 'A'
  2007 0000B171 BE00010900          <1>         mov     esi, Logical_DOSDisks
  2008 0000B176 01DE                <1> 	add	esi, ebx
  2009 0000B178 668B4E03            <1>         mov     cx, [esi+LD_FATType]
  2010                              <1> 	; CH = FS Type (A1h for FS)
  2011                              <1> 	; CL = FAT Type (0 for FS)
  2012 0000B17C 08C9                <1> 	or	cl, cl
  2013 0000B17E 7433                <1> 	jz	short loc_save_dir_buff_stc_retn
  2014                              <1> 
  2015                              <1> loc_save_dir_buffer_check_cluster_no:    
  2016 0000B180 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
  2017 0000B185 28FF                <1> 	sub	bh, bh ; ebx = 0
  2018 0000B187 09C0                <1> 	or	eax, eax
  2019 0000B189 7540                <1> 	jnz	short loc_save_sub_dir_buffer
  2020 0000B18B 8A25[6B660100]      <1> 	mov	ah, [DirBuff_FATType]
  2021 0000B191 FEC3                <1> 	inc	bl ;  bl = 1
  2022 0000B193 38DC                <1> 	cmp	ah, bl
  2023 0000B195 721D                <1> 	jb	short loc_save_dir_buff_inv_data_retn
  2024 0000B197 FEC3                <1> 	inc	bl ; bl = 2
  2025 0000B199 38E3                <1> 	cmp	bl, ah
  2026 0000B19B 7217                <1> 	jb	short loc_save_dir_buff_inv_data_retn
  2027                              <1> 
  2028                              <1> loc_save_root_dir_buffer:
  2029 0000B19D 668B5E17            <1> 	mov	bx, [esi+LD_BPB+RootDirEnts]
  2030 0000B1A1 6683C30F            <1> 	add	bx, 15
  2031 0000B1A5 66C1EB04            <1> 	shr	bx, 4 ; 16 dir entries per sector
  2032 0000B1A9 6609DB              <1> 	or	bx, bx
  2033 0000B1AC 7405                <1> 	jz	short loc_save_dir_buff_stc_retn
  2034                              <1> 	;mov	ecx, ebx 
  2035 0000B1AE 8B4664              <1> 	mov	eax, [esi+LD_ROOTBegin] ; 26/02/2016
  2036 0000B1B1 EB23                <1> 	jmp	short loc_write_directory_to_disk
  2037                              <1> 
  2038                              <1> loc_save_dir_buff_stc_retn:
  2039 0000B1B3 F9                  <1> 	stc
  2040                              <1> loc_save_dir_buff_inv_data_retn:
  2041                              <1> 	; 15/10/2016 (0Dh -> 29)
  2042 0000B1B4 B01D                <1> 	mov	al, 29 ; Invalid data !
  2043 0000B1B6 C605[6C660100]00    <1> 	mov	byte [DirBuff_ValidData], 0
  2044 0000B1BD EB05                <1> 	jmp	short loc_save_dir_buff_retn 
  2045                              <1> 
  2046                              <1> loc_write_directory_to_disk_err:
  2047                              <1> 	; 15/10/2016 (disk write error code, 1Dh -> 18)
  2048 0000B1BF B812000000          <1> 	mov	eax, 18 ; Drive not ready or write error 
  2049                              <1> 
  2050                              <1> loc_save_dir_buff_retn:
  2051 0000B1C4 BB00000800          <1> 	mov	ebx, Directory_Buffer
  2052 0000B1C9 5E                  <1> 	pop	esi
  2053 0000B1CA C3                  <1> 	retn
  2054                              <1>  
  2055                              <1> loc_save_sub_dir_buffer:
  2056                              <1> 	; ebx  = 0
  2057 0000B1CB 83E802              <1> 	sub	eax, 2
  2058 0000B1CE 8A5E13              <1> 	mov	bl, [esi+LD_BPB+SecPerClust]
  2059 0000B1D1 F7E3                <1> 	mul	ebx
  2060 0000B1D3 034668              <1>         add     eax, [esi+LD_DATABegin]
  2061                              <1>  	;mov	ecx, ebx
  2062                              <1> 
  2063                              <1> loc_write_directory_to_disk:
  2064 0000B1D6 89D9                <1>  	mov	ecx, ebx
  2065 0000B1D8 BB00000800          <1> 	mov	ebx, Directory_Buffer
  2066 0000B1DD E8D04B0000          <1> 	call	disk_write
  2067 0000B1E2 72DB                <1> 	jc	short loc_write_directory_to_disk_err
  2068                              <1> 
  2069                              <1> loc_save_dir_buff_validate_retn:
  2070 0000B1E4 C605[6C660100]01    <1> 	mov	byte [DirBuff_ValidData], 1
  2071 0000B1EB 31C0                <1> 	xor	eax, eax
  2072                              <1> 	; 26/02/2016
  2073 0000B1ED EBD5                <1> 	jmp	short loc_save_dir_buff_retn
  2074                              <1> 
  2075                              <1> update_parent_dir_lmdt:
  2076                              <1> 	; 29/12/2017
  2077                              <1> 	; 22/02/2016 (TRDOS 386 = TRDOS v2.0)
  2078                              <1> 	; 01/08/2011
  2079                              <1> 	; 16/10/2010 
  2080                              <1> 	; 
  2081                              <1> 	; INPUT -> 
  2082                              <1> 	;	none
  2083                              <1>  	; OUTPUT ->
  2084                              <1> 	;	(last modification date & time of the parent dir
  2085                              <1> 	;	will be changed/updated)
  2086                              <1> 	;
  2087                              <1> 	; (EAX, EBX, ECX, EDX, EDI will be changed)
  2088                              <1> 
  2089 0000B1EF 29C0                <1> 	sub	eax, eax
  2090 0000B1F1 8A25[445F0100]      <1> 	mov	ah, [Current_Dir_Level]
  2091 0000B1F7 A0[455F0100]        <1> 	mov	al, [Current_FATType]
  2092 0000B1FC 3C01                <1> 	cmp	al, 1
  2093 0000B1FE 723A                <1> 	jb	short loc_UPDLMDT_proc_retn
  2094                              <1>     
  2095                              <1> loc_update_parent_dir_lm_date_time:
  2096 0000B200 08E4                <1> 	or	ah, ah
  2097 0000B202 7436                <1> 	jz	short loc_UPDLMDT_proc_retn
  2098                              <1> 
  2099 0000B204 56                  <1> 	push	esi ; *
  2100 0000B205 8825[E4680100]      <1> 	mov	[UPDLMDT_CDirLevel], ah
  2101 0000B20B 8B15[405F0100]      <1> 	mov	edx, [Current_Dir_FCluster]
  2102 0000B211 8915[E5680100]      <1> 	mov	[UPDLMDT_CDirFCluster], edx
  2103                              <1> 
  2104 0000B217 FECC                <1> 	dec	ah
  2105 0000B219 B90C000000          <1> 	mov	ecx, 12
  2106 0000B21E BE[A3660100]        <1>         mov     esi, PATH_Array
  2107                              <1> 
  2108 0000B223 8825[445F0100]      <1> 	mov	[Current_Dir_Level], ah
  2109 0000B229 08E4                <1> 	or	ah, ah
  2110 0000B22B 750E                <1> 	jnz	short loc_update_parent_dir_lmdt_load_sub_dir_1
  2111 0000B22D 803D[455F0100]02    <1> 	cmp	byte [Current_FATType], 2
  2112 0000B234 770B                <1> 	ja	short loc_update_parent_dir_lmdt_load_sub_dir_2
  2113 0000B236 28C0                <1> 	sub	al, al ; eax = 0
  2114 0000B238 EB0A                <1> 	jmp	short loc_update_parent_dir_lmdt_load_sub_dir_3
  2115                              <1> 
  2116                              <1> loc_UPDLMDT_proc_retn:
  2117 0000B23A C3                  <1> 	retn
  2118                              <1>          
  2119                              <1> loc_update_parent_dir_lmdt_load_sub_dir_1:
  2120 0000B23B B010                <1> 	mov	al, 16
  2121 0000B23D F6E4                <1> 	mul	ah 
  2122 0000B23F 01C6                <1> 	add	esi, eax
  2123                              <1> 
  2124                              <1> loc_update_parent_dir_lmdt_load_sub_dir_2:  
  2125 0000B241 8B460C              <1> 	mov	eax, [esi+12] ; Parent Dir First Cluster
  2126                              <1> 
  2127                              <1> loc_update_parent_dir_lmdt_load_sub_dir_3:
  2128 0000B244 A3[405F0100]        <1> 	mov	[Current_Dir_FCluster], eax
  2129                              <1> 
  2130 0000B249 83C610              <1> 	add	esi, 16
  2131 0000B24C 66BF[CA67]          <1> 	mov	di, Dir_File_Name  
  2132 0000B250 F3A4                <1> 	rep	movsb
  2133                              <1> 	
  2134 0000B252 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2135 0000B257 29DB                <1> 	sub	ebx, ebx
  2136 0000B259 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  2137 0000B25F 01DE                <1> 	add	esi, ebx
  2138 0000B261 E88FF7FFFF          <1> 	call	reload_current_directory
  2139 0000B266 7230                <1> 	jc	short loc_update_parent_dir_lmdt_restore_cdirlevel
  2140                              <1> 
  2141                              <1> loc_update_parent_dir_lmdt_locate_dir: 
  2142 0000B268 BE[CA670100]        <1> 	mov	esi, Dir_File_Name        
  2143 0000B26D 6631C9              <1> 	xor	cx, cx
  2144 0000B270 66B81008            <1> 	mov	ax, 0810h ; Only directories
  2145 0000B274 E8B5F6FFFF          <1>         call    locate_current_dir_file
  2146                              <1> 	; EDI = DirBuff Directory Entry Address
  2147 0000B279 721D                <1> 	jc	short loc_update_parent_dir_lmdt_restore_cdirlevel
  2148                              <1> 
  2149 0000B27B E836FEFFFF          <1> 	call	convert_current_date_time
  2150 0000B280 66895712            <1> 	mov	[edi+18], dx ; Last Access Date
  2151 0000B284 66895718            <1> 	mov	[edi+24], dx ; Last Write Date
  2152 0000B288 66894716            <1> 	mov	[edi+22], ax ; Last Write Time
  2153                              <1> 
  2154 0000B28C C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  2155 0000B293 E8BCFEFFFF          <1> 	call	save_directory_buffer
  2156                              <1> 	; 29/12/2017
  2157                              <1> 	;jc	short loc_update_parent_dir_lmdt_restore_cdirlevel
  2158                              <1> 	;xor	al, al 
  2159                              <1> loc_update_parent_dir_lmdt_restore_cdirlevel:
  2160                              <1>  	;current directory level restoration
  2161 0000B298 8A25[E4680100]      <1> 	mov	ah, [UPDLMDT_CDirLevel]
  2162 0000B29E 8825[445F0100]      <1> 	mov	[Current_Dir_Level], ah
  2163 0000B2A4 8B15[E5680100]      <1>         mov     edx, [UPDLMDT_CDirFCluster]
  2164 0000B2AA 8915[405F0100]      <1> 	mov	[Current_Dir_FCluster], edx
  2165                              <1> 
  2166 0000B2B0 5E                  <1> 	pop	esi ; *
  2167 0000B2B1 C3                  <1> 	retn
  2168                              <1> 
  2169                              <1> delete_longname:
  2170                              <1> 	; 27/02/2016 (TRDOS 386 = TRDOS v2.0)
  2171                              <1> 	; 01/08/2011 (DIR.ASM, 'proc_delete_longname')
  2172                              <1> 	; 14/03/2010
  2173                              <1> 	; INPUT ->
  2174                              <1> 	; 	EAX = Directory Entry (Index) Number (< 65536)
  2175                              <1> 	; OUTPUT ->
  2176                              <1> 	;	cf = 0 -> OK  (EAX = 0)
  2177                              <1> 	; 	cf = 1 -> error code in EAX (AL)
  2178                              <1> 	;
  2179                              <1> 	; (Modified registers: EAX, EDX, ECX, EBX, EDI) 
  2180                              <1> 
  2181 0000B2B2 66A3[14690100]      <1> 	mov	[DLN_EntryNumber], ax
  2182 0000B2B8 C605[16690100]40    <1>         mov     byte [DLN_40h], 40h
  2183                              <1> 
  2184 0000B2BF E858000000          <1> 	call	locate_current_dir_entry
  2185 0000B2C4 7308                <1> 	jnc	short loc_dln_check_attributes
  2186 0000B2C6 C3                  <1> 	retn
  2187                              <1> 
  2188                              <1> loc_dln_longname_not_found:
  2189 0000B2C7 B802000000          <1> 	mov	eax, 2
  2190 0000B2CC F9                  <1> 	stc
  2191 0000B2CD C3                  <1> 	retn
  2192                              <1> 
  2193                              <1> loc_dln_check_attributes:
  2194 0000B2CE B00F                <1> 	mov	al, 0Fh  ; long name
  2195 0000B2D0 8A670B              <1> 	mov	ah, [edi+0Bh] ; dir entry attributes
  2196 0000B2D3 38C4                <1> 	cmp	ah, al
  2197 0000B2D5 75F0                <1> 	jne	short loc_dln_longname_not_found
  2198 0000B2D7 8A27                <1> 	mov	ah, [edi]
  2199 0000B2D9 2A25[16690100]      <1> 	sub	ah, [DLN_40h]
  2200 0000B2DF 76E6                <1> 	jna	short loc_dln_longname_not_found         
  2201 0000B2E1 80FC14              <1> 	cmp	ah, 14h ; 84-64=20 -> 20*13=260 bytes
  2202 0000B2E4 77E1                <1> 	ja	short loc_dln_longname_not_found
  2203                              <1>              
  2204 0000B2E6 C607E5              <1> 	mov	byte [edi], 0E5h  ; deleted sign
  2205 0000B2E9 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 ; changed/write sign
  2206 0000B2F0 C605[16690100]00    <1> 	mov	byte [DLN_40h], 0 ; 40h -> 0
  2207                              <1> 	  
  2208                              <1> loc_dln_delete_next_ln_entry:
  2209 0000B2F7 80FC01              <1> 	cmp	ah, 1
  2210 0000B2FA 7616                <1> 	jna	short loc_dln_longname_retn
  2211                              <1> loc_dln_delete_next_ln_entry_0:
  2212 0000B2FC 66FF05[14690100]    <1> 	inc	word [DLN_EntryNumber]
  2213 0000B303 0FB705[14690100]    <1> 	movzx	eax, word [DLN_EntryNumber] 
  2214 0000B30A E80D000000          <1> 	call	locate_current_dir_entry
  2215 0000B30F 73BD                <1> 	jnc	short loc_dln_check_attributes
  2216                              <1> 
  2217                              <1> loc_dln_longname_stc_retn:
  2218 0000B311 C3                  <1> 	retn 
  2219                              <1> 	   
  2220                              <1> loc_dln_longname_retn:
  2221                              <1> 	;cmp	byte [DirBuff_ValidData], 2
  2222                              <1> 	;jne	short loc_dln_longname_retn_xor_eax
  2223 0000B312 E83DFEFFFF          <1> 	call	save_directory_buffer
  2224 0000B317 72F8                <1> 	jc	short loc_dln_longname_stc_retn
  2225                              <1> 
  2226                              <1> loc_dln_longname_retn_xor_eax:
  2227 0000B319 31C0                <1> 	xor	eax, eax
  2228 0000B31B C3                  <1> 	retn
  2229                              <1> 
  2230                              <1> locate_current_dir_entry:
  2231                              <1> 	; 16/10/2016
  2232                              <1> 	; 15/10/2016
  2233                              <1> 	; 23/03/2016
  2234                              <1> 	; 27/02/2016 (TRDOS 386 = TRDOS v2.0)
  2235                              <1> 	; 01/08/2011 (DIR.ASM, 'proc_locate_current_dir_entry')
  2236                              <1> 	; 07/03/2010
  2237                              <1> 	; INPUT ->
  2238                              <1> 	;	EAX = Directory Entry (Index) Number (< 65536) 
  2239                              <1> 	; OUTPUT ->
  2240                              <1> 	;	EDI = Directory Entry Address
  2241                              <1> 	; 	EAX = Cluster Number of Directory Buffer
  2242                              <1> 	;	EBX = Directory Buffer Entry Offset
  2243                              <1> 	;	ECX = DirBuff Valid Data identifier (CL)
  2244                              <1> 	;   	If CF = 0 and CL = 2 then
  2245                              <1> 	;	   directory buffer modified and
  2246                              <1> 	;	   must be written to disk.
  2247                              <1> 	; 	If CF = 0  and CL = 1 then
  2248                              <1> 	;	   dir buffer has been written to disk, already.
  2249                              <1> 	;	CF = 1 -> Error code in EAX (AL)
  2250                              <1> 	;
  2251                              <1> 	; (Modified registers: EAX, EDX, ECX, EBX, EDI) 
  2252                              <1> 
  2253                              <1> loc_locate_current_dir_entry:
  2254 0000B31C 56                  <1> 	push	esi
  2255 0000B31D 89C1                <1> 	mov	ecx, eax
  2256 0000B31F BA20000000          <1> 	mov	edx, 32
  2257 0000B324 F7E2                <1> 	mul	edx 
  2258 0000B326 A3[20690100]        <1> 	mov	[LCDE_ByteOffset], eax
  2259 0000B32B 31DB                <1> 	xor	ebx, ebx
  2260 0000B32D 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  2261 0000B333 A0[6A660100]        <1>         mov     al, [DirBuff_DRV]
  2262 0000B338 2C41                <1> 	sub	al, 'A'
  2263 0000B33A BE00010900          <1>         mov     esi, Logical_DOSDisks
  2264 0000B33F 01DE                <1> 	add	esi, ebx
  2265 0000B341 38C7                <1> 	cmp	bh, al
  2266 0000B343 0F8592000000        <1>         jne     loc_lcde_reload_current_directory
  2267                              <1> loc_lcde_cdl_check:
  2268 0000B349 803D[445F0100]00    <1> 	cmp	byte [Current_Dir_Level], 0
  2269 0000B350 772A                <1> 	ja	short loc_lcde_calc_dirbuff_cluster_offset
  2270                              <1> 	; 27/02/2016
  2271                              <1> 	; TRDOS v1 has bug here for FAT32 fs !
  2272                              <1> 	; (Root Directory Entries for FAT32 = 0)
  2273 0000B352 807E0303            <1> 	cmp	byte [esi+LD_FATType], 3  ; FAT32
  2274 0000B356 7324                <1> 	jnb	short loc_lcde_calc_dirbuff_cluster_offset
  2275                              <1> 
  2276                              <1> loc_lcde_cdl_check_FAT12_16:
  2277 0000B358 668B4617            <1> 	mov	ax, [esi+LD_BPB+RootDirEnts]
  2278 0000B35C 6648                <1> 	dec	ax
  2279                              <1> 	;xor	dx, dx  
  2280 0000B35E 6639C8              <1> 	cmp	ax, cx ; cx = Directory Entry (Index) Number
  2281 0000B361 720E                <1> 	jb	short loc_lcde_stc_12h_retn
  2282 0000B363 66890D[18690100]    <1> 	mov	[LCDE_EntryIndex], cx
  2283 0000B36A 31C0                <1> 	xor	eax, eax
  2284 0000B36C E993000000          <1>         jmp     loc_lcde_check_dir_buffer_cluster
  2285                              <1> 
  2286                              <1> loc_lcde_stc_12h_retn:
  2287 0000B371 5E                  <1> 	pop	esi
  2288 0000B372 89CB                <1> 	mov	ebx, ecx
  2289 0000B374 89D1                <1> 	mov	ecx, edx
  2290                              <1> 	; 16/10/2016 (12h -> 12)
  2291 0000B376 B80C000000          <1> 	mov	eax, 12 ; No more files
  2292 0000B37B C3                  <1> 	retn 
  2293                              <1> 
  2294                              <1> loc_lcde_calc_dirbuff_cluster_offset:
  2295 0000B37C 8A5E13              <1> 	mov	bl, [esi+LD_BPB+SecPerClust]
  2296 0000B37F 30FF                <1> 	xor	bh, bh
  2297 0000B381 668B4611            <1> 	mov	ax, [esi+LD_BPB+BytesPerSec]
  2298 0000B385 66F7E3              <1> 	mul	bx
  2299 0000B388 6609D2              <1>  	or	dx, dx ; If bytes per cluster > 32KB it is invalid
  2300 0000B38B 755D                <1> 	jnz	short loc_lcde_invalid_format
  2301                              <1> 	;mov	ecx, eax
  2302 0000B38D 6689C1              <1> 	mov	cx, ax ; BYTES PER CLUSTER
  2303 0000B390 A1[20690100]        <1> 	mov	eax, [LCDE_ByteOffset]
  2304                              <1> 	;sub	edx, edx
  2305 0000B395 F7F1                <1> 	div	ecx
  2306 0000B397 3DFFFF0000          <1> 	cmp	eax, 65535
  2307 0000B39C 774C                <1> 	ja	short loc_lcde_invalid_format
  2308                              <1> 
  2309                              <1> 	; cluster sequence number of directory (< 65536)
  2310 0000B39E 66A3[1A690100]      <1> 	mov	[LCDE_ClusterSN], ax 
  2311                              <1> 
  2312 0000B3A4 6689D0              <1> 	mov	ax, dx ; byte offset in cluster (directory buffer)
  2313 0000B3A7 66BB2000            <1> 	mov	bx, 32 ; ; 1 dir entry = 32 bytes
  2314 0000B3AB 6629D2              <1>         sub     dx, dx  ; 0
  2315 0000B3AE 66F7F3              <1> 	div	bx 
  2316 0000B3B1 66A3[18690100]      <1> 	mov	[LCDE_EntryIndex], ax ; dir entry index/sequence number
  2317                              <1> 				      ; (in directory buffer/cluster)	  
  2318                              <1> loc_lcde_get_current_sub_dir_fcluster:
  2319 0000B3B7 A1[405F0100]        <1> 	mov	eax, [Current_Dir_FCluster]
  2320                              <1> 
  2321                              <1> loc_lcde_get_next_cluster:
  2322 0000B3BC 66833D[1A690100]00  <1> 	cmp	word [LCDE_ClusterSN], 0
  2323 0000B3C4 763E                <1> 	jna	short loc_lcde_check_dir_buffer_cluster
  2324 0000B3C6 A3[1C690100]        <1> 	mov	[LCDE_Cluster], eax
  2325 0000B3CB E834100000          <1> 	call	get_next_cluster
  2326 0000B3D0 7220                <1> 	jc	short loc_lcde_check_gnc_error
  2327 0000B3D2 66FF0D[1A690100]    <1>   	dec	word [LCDE_ClusterSN]
  2328 0000B3D9 EBE1                <1> 	jmp	short loc_lcde_get_next_cluster
  2329                              <1> 
  2330                              <1> loc_lcde_reload_current_directory:
  2331 0000B3DB 51                  <1> 	push	ecx
  2332 0000B3DC E814F6FFFF          <1> 	call	reload_current_directory
  2333 0000B3E1 59                  <1> 	pop	ecx
  2334 0000B3E2 0F8361FFFFFF        <1>         jnc     loc_lcde_cdl_check
  2335 0000B3E8 5E                  <1> 	pop	esi
  2336 0000B3E9 C3                  <1> 	retn
  2337                              <1> 
  2338                              <1> loc_lcde_invalid_format:
  2339                              <1> 	; 15/10/2016 (0Bh -> 28)
  2340 0000B3EA B81C000000          <1> 	mov	eax, 28 ; Invalid Format !
  2341                              <1> loc_lcde_drive_not_ready_read_err:
  2342 0000B3EF F9                  <1> 	stc
  2343 0000B3F0 5E                  <1> 	pop	esi 
  2344 0000B3F1 C3                  <1> 	retn  
  2345                              <1> 
  2346                              <1> loc_lcde_check_gnc_error:
  2347 0000B3F2 09C0                <1> 	or	eax, eax
  2348 0000B3F4 75F9                <1> 	jnz	short loc_lcde_drive_not_ready_read_err
  2349 0000B3F6 66FF0D[1A690100]    <1> 	dec	word [LCDE_ClusterSN]
  2350 0000B3FD 75EB                <1> 	jnz	short loc_lcde_invalid_format 
  2351 0000B3FF A1[1C690100]        <1> 	mov	eax, [LCDE_Cluster]
  2352                              <1> 
  2353                              <1> loc_lcde_check_dir_buffer_cluster:
  2354 0000B404 3B05[71660100]      <1> 	cmp	eax, [DirBuff_Cluster]
  2355 0000B40A 755C                <1> 	jne	short loc_lcde_load_dir_cluster
  2356 0000B40C 803D[6C660100]00    <1> 	cmp	byte [DirBuff_ValidData], 0
  2357 0000B413 7727                <1> 	ja	short lcde_check_dir_buffer_cluster_next
  2358 0000B415 803D[445F0100]00    <1> 	cmp	byte [Current_Dir_Level], 0    
  2359 0000B41C 775F                <1> 	ja	short loc_lcde_load_dir_cluster_0
  2360                              <1> 	; 27/02/2016
  2361                              <1> 	; TRDOS v1 has bug here for FAT32 fs !
  2362 0000B41E 807E0303            <1> 	cmp	byte [esi+LD_FATType], 3  ; FAT32
  2363 0000B422 7359                <1> 	jnb	short loc_lcde_load_dir_cluster_0
  2364                              <1> 	;
  2365 0000B424 0FB74E17            <1> 	movzx	ecx, word [esi+LD_BPB+RootDirEnts]
  2366 0000B428 6683C10F            <1> 	add	cx, 15 ; round up (16 entries per sector)
  2367 0000B42C 66C1E904            <1> 	shr	cx, 4 ; 1 sector contains 16 dir entries	
  2368                              <1> 
  2369 0000B430 8B4664              <1>         mov     eax, [esi+LD_ROOTBegin]
  2370 0000B433 EB54                <1> 	jmp	short loc_lcde_load_dir_cluster_1 
  2371                              <1> 
  2372                              <1> loc_lcde_validate_dirBuff:
  2373 0000B435 C605[6C660100]01    <1> 	mov	byte [DirBuff_ValidData], 1
  2374                              <1> 
  2375                              <1> lcde_check_dir_buffer_cluster_next:
  2376 0000B43C 0FB71D[18690100]    <1> 	movzx	ebx, word [LCDE_EntryIndex]
  2377 0000B443 663B1D[6F660100]    <1> 	cmp	bx, [DirBuff_LastEntry]
  2378 0000B44A 779E                <1> 	ja	short loc_lcde_invalid_format 
  2379 0000B44C B820000000          <1> 	mov	eax, 32
  2380 0000B451 F7E3                <1> 	mul	ebx
  2381                              <1> 	;or	edx, edx
  2382                              <1> 	;jnz	short loc_lcde_invalid_format
  2383                              <1> 
  2384 0000B453 BF00000800          <1> 	mov	edi, Directory_Buffer  
  2385 0000B458 01C7                <1> 	add	edi, eax ; add entry offset to buffer address
  2386                              <1> 
  2387                              <1> loc_lcde_dir_buffer_last_check:
  2388 0000B45A A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
  2389 0000B45F 0FB60D[6C660100]    <1> 	movzx	ecx, byte [DirBuff_ValidData]
  2390                              <1> 
  2391                              <1> loc_lcde_retn:
  2392 0000B466 5E                  <1> 	pop	esi
  2393 0000B467 C3                  <1> 	retn
  2394                              <1> 
  2395                              <1> loc_lcde_load_dir_cluster:
  2396                              <1> 	;cmp	byte [DirBuff_ValidData], 2
  2397                              <1> 	;jne	short loc_lcde_load_dir_cluster_n2
  2398 0000B468 50                  <1> 	push	eax
  2399 0000B469 E8E6FCFFFF          <1> 	call	save_directory_buffer
  2400 0000B46E 58                  <1> 	pop	eax
  2401 0000B46F 72F5                <1> 	jc	short loc_lcde_retn
  2402                              <1> 
  2403                              <1> loc_lcde_load_dir_cluster_n2:
  2404 0000B471 C605[6C660100]00    <1> 	mov	byte [DirBuff_ValidData], 0
  2405 0000B478 A3[71660100]        <1> 	mov	[DirBuff_Cluster], eax
  2406                              <1> 
  2407                              <1> loc_lcde_load_dir_cluster_0:
  2408 0000B47D 83E802              <1> 	sub	eax, 2
  2409 0000B480 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+SecPerClust]
  2410 0000B484 F7E1                <1> 	mul	ecx
  2411 0000B486 034668              <1>         add     eax, [esi+LD_DATABegin]
  2412                              <1> 
  2413                              <1> loc_lcde_load_dir_cluster_1:
  2414 0000B489 BB00000800          <1> 	mov	ebx, Directory_Buffer
  2415                              <1> 	; ecx = sector count
  2416 0000B48E E82E490000          <1> 	call	disk_read
  2417 0000B493 73A0                <1> 	jnc	short loc_lcde_validate_dirBuff
  2418                              <1> 
  2419                              <1> 	; 15/10/2016 
  2420                              <1> 	; (Disk read error instead of drv not ready err)
  2421 0000B495 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error !
  2422 0000B49A EBCA                <1> 	jmp	short loc_lcde_retn
  2423                              <1> 
  2424                              <1> 
  2425                              <1> remove_file:
  2426                              <1> 	; 15/10/2016
  2427                              <1> 	; 28/02/2016 (TRDOS 386 = TRDOS v2.0)
  2428                              <1> 	; 10/04/2011 (FILE.ASM, 'proc_delete_file')
  2429                              <1> 	; 09/08/2010
  2430                              <1> 	; INPUT ->
  2431                              <1> 	;	EDI = Directory Buffer Entry Address
  2432                              <1> 	;	 CX = Directory Buffer Entry Counter/Index
  2433                              <1> 	;	 BL = Longname Entry Length
  2434                              <1> 	;	 BH = Logical DOS Drive Number 
  2435                              <1> 
  2436 0000B49C 29C0                <1> 	sub	eax, eax
  2437 0000B49E 88FC                <1> 	mov	ah, bh
  2438 0000B4A0 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  2439 0000B4A5 01C6                <1> 	add	esi, eax
  2440                              <1> 
  2441 0000B4A7 807E0301            <1> 	cmp	byte [esi+LD_FATType], 1
  2442 0000B4AB 7312                <1> 	jnb	short loc_del_fat_file 
  2443                              <1>               
  2444 0000B4AD 807E04A1            <1> 	cmp	byte [esi+LD_FSType], 0A1h
  2445 0000B4B1 7406                <1> 	je	short loc_del_fs_file
  2446                              <1> 
  2447                              <1> loc_del_file_invalid_format:
  2448 0000B4B3 30E4                <1> 	xor	ah, ah
  2449                              <1> 	; 15/10/2016 (0Bh -> 28)
  2450 0000B4B5 B01C                <1> 	mov	al, 28  ; Invalid Format
  2451 0000B4B7 F9                  <1> 	stc 
  2452 0000B4B8 C3                  <1> 	retn
  2453                              <1> 
  2454                              <1> loc_del_fs_file:
  2455 0000B4B9 E83F0F0000          <1> 	call	delete_fs_file
  2456 0000B4BE C3                  <1> 	retn
  2457                              <1> 
  2458                              <1> loc_del_fat_file:
  2459 0000B4BF E808000000          <1> 	call	delete_directory_entry
  2460 0000B4C4 7205                <1> 	jc	short loc_del_file_err_retn 
  2461                              <1> 
  2462                              <1> loc_delfile_unlink_cluster_chain:
  2463 0000B4C6 E863170000          <1> 	call	truncate_cluster_chain
  2464                              <1> 	;jc	short loc_del_file_err_retn
  2465                              <1> 
  2466                              <1> loc_delfile_return:
  2467                              <1> loc_del_file_err_retn:
  2468 0000B4CB C3                  <1> 	retn
  2469                              <1> 
  2470                              <1> delete_directory_entry:
  2471                              <1> 	; 15/10/2016
  2472                              <1> 	; 28/02/2016 (TRDOS 386 = TRDOS v2.0)
  2473                              <1> 	; 01/08/2011 (DIR.ASM, 'proc_delete_directory_entry')
  2474                              <1> 	; 10/04/2011 
  2475                              <1> 	; INPUT ->
  2476                              <1> 	; 	ESI = Logical Dos Drive Descripton Table Address 
  2477                              <1> 	;	EDI = Directory Buffer Entry Address
  2478                              <1> 	;	 CX = Directory Buffer Entry Counter/Index
  2479                              <1> 	;	 BL = Longname Entry Length
  2480                              <1> 	; OUTPUT ->
  2481                              <1> 	; 	ESI = Logical dos drive descripton table address 
  2482                              <1> 	;	EAX = First cluster to be truncated/unlinked
  2483                              <1> 	;       CF = 1 -> Error code in EAX (AL)
  2484                              <1> 	;       CF = 0 & BH <> 0 -> LMDT write error  (BH = 1)
  2485                              <1> 	;       CF = 0 & BL <> 0 -> Long name delete error (BL = FFh) 
  2486                              <1> 	;
  2487                              <1> 	;  (EDI, EBX, ECX register contents will be changed)
  2488                              <1> 
  2489 0000B4CC 881D[AE680100]      <1> 	mov	[DelFile_LNEL], bl
  2490 0000B4D2 66890D[AC680100]    <1> 	mov	[DelFile_EntryCounter], cx
  2491                              <1> 
  2492 0000B4D9 668B4714            <1> 	mov	ax, [edi+20] ; First Cluster High Word
  2493 0000B4DD C1E010              <1> 	shl	eax, 16
  2494 0000B4E0 668B471A            <1> 	mov	ax, [edi+26] ; First Cluster Low Word
  2495                              <1> 
  2496 0000B4E4 A3[A8680100]        <1> 	mov	[DelFile_FCluster], eax
  2497                              <1> 
  2498                              <1> loc_del_short_name:
  2499 0000B4E9 C607E5              <1> 	mov	byte [edi], 0E5h  ; Deleted sign
  2500                              <1> 
  2501 0000B4EC C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  2502 0000B4F3 E85CFCFFFF          <1> 	call	save_directory_buffer
  2503 0000B4F8 723D                <1> 	jc	short loc_delete_direntry_err_return
  2504                              <1>  
  2505                              <1> loc_del_long_name:
  2506 0000B4FA 0FB615[AE680100]    <1> 	movzx	edx, byte [DelFile_LNEL]
  2507 0000B501 08D2                <1> 	or	dl, dl
  2508 0000B503 7416                <1> 	jz	short loc_del_dir_entry_update_parent_dir_lm_date
  2509                              <1> 
  2510 0000B505 8835[AE680100]      <1> 	mov	byte [DelFile_LNEL], dh ; 0              
  2511                              <1>   
  2512 0000B50B 0FB705[AC680100]    <1> 	movzx	eax,  word [DelFile_EntryCounter]
  2513 0000B512 29D0                <1> 	sub	eax, edx
  2514                              <1> 	;jnc	short loc_del_long_name_continue
  2515 0000B514 7205                <1> 	jc	short loc_del_dir_entry_update_parent_dir_lm_date   
  2516                              <1> 
  2517                              <1> ;loc_del_direntry_inv_data_return: ; 15/10/2016 (0Dh -> 29)
  2518                              <1> ;	mov	eax, 29 ; 0Dh (TRDOS 8086) ; Invalid data
  2519                              <1> ;	retn
  2520                              <1> 
  2521                              <1> loc_del_long_name_continue: 
  2522                              <1> 	; AX = Directory Entry Number of the long name last entry
  2523 0000B516 E897FDFFFF          <1> 	call	delete_longname
  2524                              <1> 	;jc	short loc_delete_direntry_err_return
  2525                              <1> 
  2526                              <1> loc_del_dir_entry_update_parent_dir_lm_date:
  2527 0000B51B 801D[AE680100]00    <1> 	sbb	byte [DelFile_LNEL], 0 ; 0FFh if cf = 1
  2528                              <1> 
  2529 0000B522 E8C8FCFFFF          <1> 	call	update_parent_dir_lmdt
  2530 0000B527 B700                <1> 	mov	bh, 0
  2531 0000B529 80D700              <1> 	adc	bh, 0
  2532                              <1> 
  2533 0000B52C 8A1D[AE680100]      <1> 	mov	bl, byte [DelFile_LNEL]
  2534                              <1>  
  2535                              <1> loc_delete_direntry_return:
  2536 0000B532 A1[A8680100]        <1> 	mov	eax, [DelFile_FCluster]
  2537                              <1> loc_delete_direntry_err_return:
  2538 0000B537 C3                  <1> 	retn
  2539                              <1> 
  2540                              <1> rename_directory_entry:
  2541                              <1> 	; 13/11/2017
  2542                              <1> 	; 15/10/2016
  2543                              <1> 	; 06/03/2016 (TRDOS 386 = TRDOS v2.0)
  2544                              <1> 	; 01/08/2011 (DIR.ASM, 'proc_rename_directory_entry')
  2545                              <1> 	; 19/11/2010
  2546                              <1> 	; INPUT -> (Current Directory)
  2547                              <1> 	;	CX = Directory Entry Number
  2548                              <1> 	;      EAX = First Cluster number of file or directory
  2549                              <1> 	;      EBX = Longname Length (dir entry count) (< 256)
  2550                              <1> 	;      ESI = New file (or directory) name (no path).
  2551                              <1> 	;           (ASCIIZ string)  
  2552                              <1> 	; OUTPUT -> 
  2553                              <1> 	;      CF = 0 -> successfull
  2554                              <1> 	;      CF = 1 -> error code in EAX (AL)
  2555                              <1> 	;
  2556                              <1> 	; (EAX, EBX, ECX, EDX, ESI, EDI will be changed)
  2557                              <1> 
  2558 0000B538 803D[455F0100]00    <1> 	cmp	byte [Current_FATType], 0
  2559 0000B53F 7706                <1> 	ja	short loc_rename_directory_entry
  2560                              <1> 
  2561 0000B541 E8B80E0000          <1> 	call	rename_fs_file_or_directory
  2562 0000B546 C3                  <1> 	retn 
  2563                              <1> 	
  2564                              <1> loc_rename_directory_entry:
  2565 0000B547 881D[AE680100]      <1> 	mov	[DelFile_LNEL], bl
  2566 0000B54D 66890D[AC680100]    <1> 	mov	[DelFile_EntryCounter], cx
  2567 0000B554 A3[A8680100]        <1> 	mov	[DelFile_FCluster], eax
  2568                              <1> 
  2569 0000B559 0FB7C1              <1> 	movzx	eax, cx
  2570 0000B55C E8BBFDFFFF          <1> 	call	locate_current_dir_entry
  2571 0000B561 7308                <1> 	jnc	short loc_rename_direntry_check_fcluster
  2572                              <1> 
  2573                              <1> loc_rename_direntry_pop_retn:
  2574 0000B563 C3                  <1> 	retn
  2575                              <1> 
  2576                              <1> loc_rename_direntry_pop_invd_retn:
  2577 0000B564 F9                  <1> 	stc
  2578                              <1> loc_rename_direntry_invd_retn:
  2579                              <1> 	; 15/10/2016 (0Dh -> 29)
  2580 0000B565 B81D000000          <1> 	mov	eax, 29 ; Invalid data
  2581                              <1> loc_rename_retn:
  2582 0000B56A C3                  <1> 	retn 
  2583                              <1> 
  2584                              <1> loc_rename_direntry_check_fcluster:
  2585 0000B56B 668B5714            <1> 	mov	dx, [edi+20] ; First Cluster HW
  2586 0000B56F C1E210              <1> 	shl	edx, 16 ; 13/11/2017
  2587 0000B572 668B571A            <1> 	mov	dx, [edi+26] ; First Cluster LW
  2588 0000B576 3B15[A8680100]      <1> 	cmp	edx, [DelFile_FCluster]
  2589 0000B57C 75E6                <1> 	jne	short loc_rename_direntry_pop_invd_retn
  2590                              <1> 	; ESI = New file (or directory) name. (ASCIIZ string)
  2591                              <1> 	; 06/03/2016
  2592                              <1> 	; TRDOS v2 - NOTE: 'convert_file_name' procedure
  2593                              <1> 	; has been modified for eliminating following situation.
  2594                              <1> 	; 
  2595                              <1> 	; TRDOS v1 - NOTE: If file/dir name is more than 11 bytes
  2596                              <1> 	; without a dot, attributes (edi+11) byte will be overwritten !
  2597                              <1> 	; (Dot file name input must be proper for 11 byte dir entry
  2598                              <1> 	;  type file name output.) 
  2599 0000B57E E8A2F6FFFF          <1> 	call	convert_file_name
  2600                              <1> 
  2601 0000B583 C605[6C660100]02    <1>         mov     byte [DirBuff_ValidData], 2
  2602 0000B58A E8C5FBFFFF          <1> 	call	save_directory_buffer
  2603 0000B58F 72D9                <1> 	jc	short loc_rename_retn
  2604                              <1> 
  2605                              <1> loc_rename_direntry_del_ln:
  2606 0000B591 0FB615[AE680100]    <1> 	movzx	edx, byte [DelFile_LNEL]
  2607 0000B598 08D2                <1> 	or	dl, dl
  2608 0000B59A 7410                <1> 	jz	short loc_rename_direntry_update_parent_dir_lm_date
  2609                              <1> 
  2610 0000B59C 0FB705[AC680100]    <1> 	movzx	eax, word [DelFile_EntryCounter]
  2611 0000B5A3 29D0                <1> 	sub	eax, edx
  2612 0000B5A5 72BE                <1> 	jc	short loc_rename_direntry_invd_retn
  2613                              <1> 
  2614                              <1> loc_rename_direntry_del_ln_continue: 
  2615                              <1> 	; EAX = Directory Entry Number of the long name last entry
  2616 0000B5A7 E806FDFFFF          <1> 	call	delete_longname
  2617                              <1> 
  2618                              <1> loc_rename_direntry_update_parent_dir_lm_date:
  2619 0000B5AC E83EFCFFFF          <1> 	call	update_parent_dir_lmdt
  2620 0000B5B1 31C0                <1> 	xor	eax, eax 
  2621 0000B5B3 C3                  <1> 	retn
  2622                              <1> 
  2623                              <1> move_source_file_to_destination_file:
  2624                              <1> 	; 15/10/2016
  2625                              <1> 	; 11/03/2016
  2626                              <1> 	; 10/03/2016 (TRDOS 386 = TRDOS v2.0)
  2627                              <1> 	; 01/08/2011 (FILE.ASM)
  2628                              <1> 	; 04/08/2010
  2629                              <1> 	;
  2630                              <1> 	;   Phase 1 -> Check destination file, 
  2631                              <1> 	;              'not found' is required
  2632                              <1> 	;   Phase 2 -> Check source file
  2633                              <1> 	;              'found' and proper attributes is required
  2634                              <1> 	;   Phase 3 -> Make destination directory entry,
  2635                              <1> 	;           add new dir cluster or section if it is required
  2636                              <1> 	;   Phase 4 -> Delete source directory entry.
  2637                              <1> 	;       cf = 1 causes to return before the phase 4.
  2638                              <1> 	;    (source file protection against any possible errors)    
  2639                              <1> 	;
  2640                              <1> 	; 08/05/2011 major modification
  2641                              <1> 	;            -> destination file deleting is removed   
  2642                              <1> 	;            for msdos move/rename compatibility.
  2643                              <1> 	;            (Access denied error will return if
  2644                              <1> 	;            the destination file is found...)
  2645                              <1> 	; INPUT ->
  2646                              <1> 	;	 ESI = Source File Pathname (Asciiz)
  2647                              <1> 	;        EDI = Destination File Pathname (Asciiz)
  2648                              <1> 	;        AL = 0 --> Interrupt (System call)
  2649                              <1> 	;        AL > 0 --> Command Interpreter (Question)
  2650                              <1> 	;        AL = 1 --> Question Phase
  2651                              <1> 	;        AL = 2 --> Progress Phase        
  2652                              <1> 	; OUTPUT -> 
  2653                              <1> 	;	 cf = 0 -> OK
  2654                              <1> 	;        EAX = Destination directory first cluster
  2655                              <1> 	;        ESI = Logical DOS drive description table 
  2656                              <1> 	;        EBX = Destination file structure offset
  2657                              <1> 	;        CX = 0 (CX > 0 --> calculate free space error)
  2658                              <1> 	;        cf = 1 -> Error code in EAX (AL) 
  2659                              <1> 	;
  2660                              <1> 	;  (EDX, ECX, EBX, ESI, EDI will be changed)
  2661                              <1> 
  2662 0000B5B4 3C02                <1> 	cmp	al, 2
  2663 0000B5B6 0F847F010000        <1> 	je	msftdf_df2_check_directory
  2664 0000B5BC A2[2E6A0100]        <1> 	mov	[move_cmd_phase], al
  2665                              <1> 
  2666                              <1> msftdf_parse_sf_path:
  2667                              <1> 	; ESI = ASCIIZ pathname (Source)
  2668 0000B5C1 57                  <1> 	push	edi 
  2669 0000B5C2 BF[2C690100]        <1> 	mov	edi, SourceFile_Drv
  2670 0000B5C7 E824F7FFFF          <1> 	call	parse_path_name
  2671 0000B5CC 5E                  <1> 	pop	esi
  2672 0000B5CD 7211                <1> 	jc	short msftdf_psf_retn
  2673                              <1> 
  2674                              <1> msftdf_parse_df_path:
  2675                              <1> 	; ESI = ASCIIZ pathname	(Destination)
  2676 0000B5CF BF[AC690100]        <1> 	mov	edi, DestinationFile_Drv
  2677 0000B5D4 E817F7FFFF          <1> 	call	parse_path_name
  2678 0000B5D9 7306                <1> 	jnc	short msftdf_check_sf_drv
  2679                              <1> 
  2680 0000B5DB 3C01                <1> 	cmp	al, 1 ; File or directory name is not existing
  2681 0000B5DD 7602                <1> 	jna	short msftdf_check_sf_drv
  2682                              <1> 
  2683                              <1> msftdf_stc_retn:
  2684 0000B5DF F9                  <1> 	stc
  2685                              <1> msftdf_psf_retn:
  2686 0000B5E0 C3                  <1> 	retn 
  2687                              <1> 
  2688                              <1> msftdf_check_sf_drv:
  2689 0000B5E1 A0[2C690100]        <1> 	mov	al, [SourceFile_Drv]
  2690                              <1> 
  2691                              <1> msftdf_check_df_drv:
  2692 0000B5E6 8A15[AC690100]      <1> 	mov	dl, [DestinationFile_Drv]
  2693                              <1> 
  2694                              <1> msftdf_compare_sf_df_drv:
  2695 0000B5EC 29DB                <1> 	sub	ebx, ebx
  2696 0000B5EE 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  2697 0000B5F4 38C2                <1> 	cmp	dl, al
  2698 0000B5F6 7409                <1> 	je	short msftdf_check_sf_df_drv_ok
  2699                              <1> 
  2700                              <1> msftdf_not_same_drv:
  2701                              <1>         ; DL = source file's drive number
  2702 0000B5F8 88C6                <1> 	mov	dh, al ; destination file's drive number
  2703                              <1> 	; 15/10/2016 (11h -> 21)
  2704 0000B5FA B815000000          <1> 	mov	eax, 21 ; Not the same drive
  2705 0000B5FF F9                  <1> 	stc
  2706 0000B600 C3                  <1> 	retn 
  2707                              <1> 
  2708                              <1> msftdf_check_sf_df_drv_ok:
  2709 0000B601 8815[2F6A0100]      <1> 	mov	[msftdf_sf_df_drv], dl
  2710                              <1> 
  2711 0000B607 29C0                <1>         sub	eax, eax
  2712 0000B609 88D4                <1> 	mov	ah, dl
  2713 0000B60B 0500010900          <1> 	add	eax, Logical_DOSDisks
  2714 0000B610 A3[306A0100]        <1> 	mov	[msftdf_drv_offset], eax
  2715                              <1> 
  2716 0000B615 38FA                <1> 	cmp	dl, bh ; byte [Current_Drv]
  2717 0000B617 7407                <1> 	je	short msftdf_df_check_directory
  2718                              <1> 
  2719                              <1> msftdf_change_drv:
  2720 0000B619 E85EC1FFFF          <1> 	call 	change_current_drive
  2721 0000B61E 726D                <1> 	jc	short msftdf_df_error_retn
  2722                              <1> 	  
  2723                              <1> msftdf_check_destination_file:
  2724                              <1> msftdf_df_check_directory:
  2725 0000B620 BE[AD690100]        <1> 	mov	esi, DestinationFile_Directory
  2726 0000B625 803E20              <1> 	cmp	byte [esi], 20h
  2727 0000B628 760F                <1> 	jna	short msftdf_df_find_1
  2728                              <1> 
  2729                              <1> msftdf_df_change_directory:
  2730 0000B62A FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  2731 0000B630 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  2732 0000B632 E8A3F0FFFF          <1> 	call	change_current_directory
  2733 0000B637 7254                <1> 	jc	short msftdf_df_error_retn
  2734                              <1> 
  2735                              <1> ;msftdf_df_change_prompt_dir_string:
  2736                              <1> ;	call 	change_prompt_dir_string
  2737                              <1> 
  2738                              <1> msftdf_df_find_1:
  2739 0000B639 BE[EE690100]        <1>         mov     esi, DestinationFile_Name
  2740 0000B63E 803E20              <1> 	cmp	byte [esi], 20h
  2741 0000B641 7631                <1> 	jna	short msftdf_df_copy_sf_name
  2742                              <1> 
  2743                              <1> msftdf_df_find_2:
  2744 0000B643 6631C0              <1> 	xor	ax, ax ; DestinationFile_AttributesMask -> any/zero
  2745 0000B646 E8D4D4FFFF          <1> 	call	find_first_file
  2746 0000B64B 0F838D000000        <1> 	jnc	msftdf_permission_denied_retn
  2747                              <1> 
  2748                              <1> msftdf_df_check_error_code:
  2749                              <1> 	;cmp	eax, 2 ; File not found error
  2750 0000B651 3C02                <1> 	cmp	al, 2
  2751 0000B653 7537                <1> 	jne	short msftdf_df_stc_retn
  2752                              <1>               
  2753                              <1> msftdf_df_check_fname:
  2754                              <1> 	; 15/10/2016
  2755 0000B655 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name ; *
  2756 0000B65A E87ED8FFFF          <1> 	call	check_filename
  2757 0000B65F 7307                <1> 	jnc	short msftdf_convert_df_direntry_name
  2758                              <1> 	; invalid file name chars !
  2759 0000B661 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME  ; 26
  2760 0000B666 EB24                <1> 	jmp	short msftdf_df_stc_retn
  2761                              <1> 
  2762                              <1> msftdf_convert_df_direntry_name:
  2763                              <1> 	; mov	esi, DestinationFile_Name ; *
  2764 0000B668 BF[FE690100]        <1> 	mov	edi, DestinationFile_DirEntry
  2765 0000B66D E8B3F5FFFF          <1> 	call	convert_file_name
  2766 0000B672 EB1A                <1>   	jmp	short msftdf_restore_current_dir_1
  2767                              <1> 
  2768                              <1> msftdf_df_copy_sf_name:
  2769 0000B674 89F7                <1> 	mov	edi, esi
  2770 0000B676 57                  <1> 	push	edi 
  2771 0000B677 BE[6E690100]        <1>         mov     esi, SourceFile_Name
  2772 0000B67C B90C000000          <1> 	mov	ecx, 12
  2773                              <1> msftdf_df_copy_sf_name_loop:
  2774 0000B681 AC                  <1> 	lodsb
  2775 0000B682 AA                  <1>         stosb
  2776 0000B683 08C0                <1> 	or	al, al
  2777 0000B685 7402                <1> 	jz	short msftdf_df_copy_sf_name_ok	
  2778 0000B687 E2F8                <1>         loop    msftdf_df_copy_sf_name_loop
  2779                              <1> msftdf_df_copy_sf_name_ok:	
  2780 0000B689 5E                  <1> 	pop	esi  
  2781 0000B68A EBB7                <1> 	jmp	short msftdf_df_find_2
  2782                              <1> 
  2783                              <1> msftdf_df_stc_retn:
  2784 0000B68C F9                  <1> 	stc
  2785                              <1> msftdf_restore_cdir_failed:
  2786                              <1> msftdf_df_error_retn:
  2787 0000B68D C3                  <1> 	retn
  2788                              <1> 
  2789                              <1> msftdf_restore_current_dir_1:
  2790 0000B68E 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  2791 0000B695 760D                <1> 	jna	short msftdf_sf_check_directory
  2792 0000B697 8B35[306A0100]      <1> 	mov	esi, [msftdf_drv_offset] 
  2793 0000B69D E891C1FFFF          <1> 	call	restore_current_directory
  2794 0000B6A2 72E9                <1> 	jc	short msftdf_restore_cdir_failed
  2795                              <1> 
  2796                              <1> msftdf_sf_check_directory:
  2797 0000B6A4 BE[2D690100]        <1> 	mov	esi, SourceFile_Directory
  2798 0000B6A9 803E20              <1> 	cmp	byte [esi], 20h
  2799 0000B6AC 760F                <1> 	jna	short msftdf_sf_find
  2800                              <1> msftdf_sf_change_directory:
  2801 0000B6AE FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  2802 0000B6B4 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  2803 0000B6B6 E81FF0FFFF          <1> 	call	change_current_directory
  2804 0000B6BB 7227                <1> 	jc	short msftdf_return
  2805                              <1> 
  2806                              <1> ;msftdf_sf_change_prompt_dir_string:
  2807                              <1> ;	call	change_prompt_dir_string
  2808                              <1> 
  2809                              <1> msftdf_sf_find:
  2810 0000B6BD BE[6E690100]        <1>         mov     esi, SourceFile_Name  ; Offset 66
  2811 0000B6C2 66B80018            <1> 	mov	ax, 1800h ; Only files
  2812 0000B6C6 E854D4FFFF          <1> 	call	find_first_file
  2813 0000B6CB 7217                <1> 	jc	short msftdf_return
  2814                              <1> 
  2815                              <1> msftdf_sf_ambgfn_check:
  2816 0000B6CD 6609D2              <1> 	or	dx, dx ; Ambiguous filename chars used sign (DX>0)
  2817 0000B6D0 7407                <1> 	jz	short msftdf_sf_found
  2818                              <1> 
  2819                              <1> msftdf_ambiguous_file_name_error:
  2820 0000B6D2 B802000000          <1> 	mov	eax, 2 ; File not found error
  2821 0000B6D7 F9                  <1> 	stc
  2822 0000B6D8 C3                  <1> 	retn
  2823                              <1> 
  2824                              <1> msftdf_sf_found:
  2825 0000B6D9 80E31F              <1> 	and	bl, 1Fh ; Attributes, D-V-S-H-R
  2826 0000B6DC 7416                <1> 	jz	short msftdf_save_sf_structure
  2827                              <1> 
  2828                              <1> msftdf_permission_denied_retn:
  2829 0000B6DE B805000000          <1> 	mov	eax, 05h ; Access (Permission) denied !
  2830 0000B6E3 F9                  <1> 	stc
  2831                              <1> msftdf_rest_cdir_err_retn:
  2832                              <1> msftdf_return:
  2833 0000B6E4 C3                  <1> 	retn
  2834                              <1> 
  2835                              <1> msftdf_phase_1_return:
  2836 0000B6E5 31C0                <1> 	xor	eax, eax
  2837 0000B6E7 A2[2E6A0100]        <1> 	mov	[move_cmd_phase], al ; 0
  2838 0000B6EC FEC0                <1> 	inc	al ; mov al, 1
  2839 0000B6EE BB[3BB70000]        <1> 	mov	ebx, msftdf_df2_check_directory
  2840                              <1> 	;mov	edx, 0FFFFFFFFh 
  2841 0000B6F3 C3                  <1> 	retn
  2842                              <1> 
  2843                              <1> msftdf_save_sf_structure:
  2844 0000B6F4 BE[38680100]        <1> 	mov	esi, FindFile_DirEntry
  2845 0000B6F9 BF[7E690100]        <1> 	mov	edi, SourceFile_DirEntry
  2846 0000B6FE B908000000          <1> 	mov	ecx, 8
  2847 0000B703 F3A5                <1> 	rep	movsd
  2848                              <1> 
  2849                              <1> msftdf_df_copy_sf_parameters:
  2850 0000B705 BE0B000000          <1> 	mov	esi, 11
  2851 0000B70A 89F7                <1> 	mov	edi, esi
  2852 0000B70C 81C6[7E690100]      <1> 	add	esi, SourceFile_DirEntry
  2853 0000B712 81C7[FE690100]      <1> 	add	edi, DestinationFile_DirEntry
  2854                              <1> 	;mov	ecx, 21
  2855 0000B718 B115                <1> 	mov	cl, 21
  2856 0000B71A F3A4                <1> 	rep	movsb
  2857                              <1> 
  2858                              <1> msftdf_restore_current_dir_2:
  2859 0000B71C 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  2860 0000B723 760D                <1> 	jna	short msftdf_df2_check_move_cmd_phase
  2861 0000B725 8B35[306A0100]      <1>  	mov	esi, [msftdf_drv_offset]
  2862 0000B72B E803C1FFFF          <1> 	call	restore_current_directory
  2863 0000B730 72B2                <1> 	jc	short msftdf_rest_cdir_err_retn
  2864                              <1> 
  2865                              <1> msftdf_df2_check_move_cmd_phase:
  2866 0000B732 803D[2E6A0100]01    <1> 	cmp	byte [move_cmd_phase], 1
  2867 0000B739 74AA                <1> 	je	short msftdf_phase_1_return
  2868                              <1> 
  2869                              <1> msftdf_df2_check_directory:
  2870 0000B73B BE[AD690100]        <1> 	mov	esi, DestinationFile_Directory
  2871 0000B740 803E20              <1> 	cmp	byte [esi], 20h
  2872 0000B743 760F                <1> 	jna	short msftdf_make_dfde_locate_ffe_on_directory
  2873                              <1> msftdf_df2_change_directory:
  2874 0000B745 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  2875 0000B74B 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  2876 0000B74D E888EFFFFF          <1> 	call	change_current_directory
  2877 0000B752 7290                <1> 	jc	short msftdf_return
  2878                              <1> 
  2879                              <1> ;msftdf_df2_change_prompt_dir_string:
  2880                              <1> ;	call	change_prompt_dir_string
  2881                              <1> 
  2882                              <1> msftdf_make_dfde_locate_ffe_on_directory:
  2883                              <1> 	; Current directory fcluster <> Directory buffer cluster
  2884                              <1> 	; Current directory will be reloaded by
  2885                              <1> 	; 'locate_current_dir_file' procedure
  2886                              <1> 	;
  2887                              <1> 	;xor	ax, ax
  2888 0000B754 31C0                <1> 	xor	eax, eax
  2889 0000B756 89C1                <1> 	mov	ecx, eax
  2890 0000B758 6649                <1> 	dec	cx ; FFFFh  
  2891                              <1> 		; CX = FFFFh -> find first deleted or free entry
  2892                              <1> 		; ESI would be ASCIIZ filename address if the call
  2893                              <1> 		; would not be for first free or deleted dir entry  
  2894 0000B75A E8CFF1FFFF          <1> 	call	locate_current_dir_file
  2895 0000B75F 733F                <1> 	jnc	msftdf_make_dfde_set_ff_dir_entry
  2896                              <1> 	
  2897                              <1> 	;cmp	eax, 2
  2898 0000B761 3C02                <1>         cmp	al, 2
  2899 0000B763 7537                <1> 	jne	short msftdf_error_retn
  2900                              <1> 
  2901                              <1> msftdf_add_new_dir_entry_check_fs:
  2902 0000B765 8B35[306A0100]      <1> 	mov	esi, [msftdf_drv_offset]
  2903 0000B76B A1[71660100]        <1> 	mov 	eax, [DirBuff_Cluster]
  2904 0000B770 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  2905 0000B774 7711                <1> 	ja	short msftdf_add_new_subdir_cluster
  2906                              <1> 
  2907                              <1> msftdf_add_new_fs_subdir_section:
  2908                              <1> 	;CL=0, CH=E5h --> deleted entry, CH=0 --> free entry
  2909                              <1>         ;xor	cx, cx
  2910 0000B776 30ED                <1> 	xor	ch, ch ; cx = 0 --> add a new subdir section
  2911 0000B778 E8830C0000          <1> 	call	add_new_fs_section
  2912 0000B77D 721E                <1>         jc	short msftdf_dsfde_error_retn
  2913                              <1> 	;mov	[createfile_LastDirCluster], eax
  2914                              <1> 
  2915 0000B77F E8A30E0000          <1> 	call	load_FS_sub_directory 
  2916                              <1> 	;mov	ebx, Directory_Buffer 
  2917 0000B784 7318                <1> 	jnc	short msftdf_add_new_fs_subdir_section_ok
  2918 0000B786 C3                  <1> 	retn	 
  2919                              <1> 
  2920                              <1> msftdf_add_new_subdir_cluster:
  2921 0000B787 E881150000          <1> 	call	add_new_cluster
  2922 0000B78C 720F                <1> 	jc	short msftdf_dsfde_error_retn
  2923                              <1> 	
  2924                              <1> 	;mov	[createfile_LastDirCluster], eax
  2925                              <1> 
  2926 0000B78E E8570E0000          <1> 	call	load_FAT_sub_directory
  2927 0000B793 7309                <1> 	jnc	short msftdf_add_new_subdir_cluster_ok
  2928                              <1> 	; EBX = Directory buffer address
  2929                              <1> 
  2930                              <1> msftdf_ansdc_update_parent_dir_lmdt:
  2931                              <1> msftdf_make_dfde_err_upd_pdir_lmdt:
  2932 0000B795 50                  <1> 	push	eax
  2933 0000B796 E854FAFFFF          <1> 	call	update_parent_dir_lmdt
  2934 0000B79B 58                  <1> 	pop	eax
  2935                              <1> 
  2936                              <1> msftdf_error_retn:
  2937 0000B79C F9                  <1> 	stc
  2938                              <1> msftdf_dsfde_restore_cdir_failed:
  2939                              <1> msftdf_dsfde_error_retn:
  2940 0000B79D C3                  <1> 	retn
  2941                              <1> 
  2942                              <1> msftdf_add_new_fs_subdir_section_ok:
  2943                              <1> msftdf_add_new_subdir_cluster_ok:
  2944 0000B79E 89DF                <1> 	mov	edi, ebx ; Directory buffer address
  2945                              <1> 
  2946                              <1> msftdf_make_dfde_set_ff_dir_entry:
  2947 0000B7A0 8B15[405F0100]      <1> 	mov	edx, [Current_Dir_FCluster]
  2948 0000B7A6 8915[946A0100]      <1> 	mov	[createfile_FFCluster], edx
  2949                              <1> 	; EDI = Directory entry offset
  2950 0000B7AC BE[FE690100]        <1> 	mov	esi, DestinationFile_DirEntry
  2951 0000B7B1 B908000000          <1> 	mov	ecx, 8
  2952 0000B7B6 F3A5                <1> 	rep	movsd
  2953                              <1> 
  2954 0000B7B8 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 
  2955 0000B7BF E890F9FFFF          <1> 	call	save_directory_buffer
  2956 0000B7C4 72CF                <1> 	jc	short msftdf_make_dfde_err_upd_pdir_lmdt
  2957                              <1> 
  2958                              <1> msftdf_make_dfde_update_pdir_lmdt:
  2959 0000B7C6 E824FAFFFF          <1> 	call	update_parent_dir_lmdt
  2960                              <1> 
  2961                              <1> msftdf_dsfde_restore_current_dir_1:
  2962 0000B7CB 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  2963 0000B7D2 760D                <1> 	jna	short msftdf_dsfde_check_directory
  2964 0000B7D4 8B35[306A0100]      <1>  	mov	esi, [msftdf_drv_offset]
  2965 0000B7DA E854C0FFFF          <1> 	call	restore_current_directory
  2966 0000B7DF 72BC                <1> 	jc	short msftdf_dsfde_restore_cdir_failed
  2967                              <1> 
  2968                              <1> msftdf_dsfde_check_directory:
  2969 0000B7E1 BE[2D690100]        <1> 	mov	esi, SourceFile_Directory
  2970 0000B7E6 803E20              <1> 	cmp	byte [esi], 20h
  2971 0000B7E9 760F                <1> 	jna	short msftdf_dsfde_find_file
  2972                              <1> 
  2973                              <1> msftdf_dsfde_change_directory:
  2974 0000B7EB FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  2975 0000B7F1 28E4                <1> 	sub	ah, ah ; CD_COMMAND sign -> 0 
  2976 0000B7F3 E8E2EEFFFF          <1> 	call	change_current_directory
  2977 0000B7F8 72A3                <1> 	jc	short msftdf_dsfde_error_retn
  2978                              <1> 
  2979                              <1> ;msftdf_dsfde_sf_change_prompt_dir_string:
  2980                              <1> ;	call	change_prompt_dir_string
  2981                              <1> 
  2982                              <1> msftdf_dsfde_find_file:
  2983 0000B7FA BE[6E690100]        <1> 	mov	esi, SourceFile_Name  ; Offset 66
  2984 0000B7FF 668B460E            <1> 	mov	ax, [esi+14] ; 80 -> SourceFile_AttributesMask
  2985 0000B803 E817D3FFFF          <1> 	call	find_first_file
  2986 0000B808 7293                <1> 	jc	short msftdf_dsfde_error_retn
  2987                              <1> 
  2988                              <1> msftdf_dsfde_delete_direntry:
  2989 0000B80A 8B35[306A0100]      <1> 	mov	esi, [msftdf_drv_offset]
  2990                              <1> 	
  2991 0000B810 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  2992 0000B814 770A                <1> 	ja	short msftdf_delete_FAT_direntry
  2993                              <1> 	
  2994 0000B816 30DB                <1> 	xor	bl, bl
  2995                              <1> 	; BL = 0 -> File
  2996                              <1> 	; EDI -> Directory buffer entry offset/address 
  2997 0000B818 E8E40B0000          <1> 	call	delete_fs_directory_entry
  2998 0000B81D 7315                <1> 	jnc	short msftdf_dsfde_restore_current_dir_2
  2999 0000B81F C3                  <1> 	retn
  3000                              <1> 
  3001                              <1> msftdf_delete_FAT_direntry:	
  3002 0000B820 8A1D[35680100]      <1> 	mov	bl, [FindFile_LongNameEntryLength]
  3003 0000B826 668B0D[60680100]    <1> 	mov	cx, [FindFile_DirEntryNumber]
  3004                              <1> 	; ESI = Logical DOS drive description table address
  3005                              <1> 	; EDI = Directory buffer entry offset/address 
  3006 0000B82D E89AFCFFFF          <1> 	call	delete_directory_entry
  3007 0000B832 721C                <1> 	jc	short msftdf_retn
  3008                              <1> 
  3009                              <1> msftdf_dsfde_restore_current_dir_2:
  3010 0000B834 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  3011 0000B83B 7607                <1> 	jna	short msftdf_new_dir_fcluster_retn
  3012                              <1> 	;mov	esi, [msftdf_drv_offset]
  3013 0000B83D E8F1BFFFFF          <1> 	call	restore_current_directory
  3014 0000B842 720C                <1> 	jc	short msftdf_retn
  3015                              <1> 
  3016                              <1> msftdf_new_dir_fcluster_retn:
  3017 0000B844 31C9                <1> 	xor	ecx, ecx 
  3018 0000B846 A1[946A0100]        <1> 	mov	eax, [createfile_FFCluster]
  3019 0000B84B BB[AC690100]        <1> 	mov	ebx, DestinationFile_Drv
  3020                              <1> 
  3021                              <1> msftdf_retn:
  3022 0000B850 C3                  <1> 	retn
  3023                              <1> 
  3024                              <1> 
  3025                              <1> copy_source_file_to_destination_file:
  3026                              <1> 	; 17/10/2016
  3027                              <1> 	; 16/10/2016
  3028                              <1> 	; 15/10/2016
  3029                              <1> 	; 30/03/2016, 31/03/2016
  3030                              <1> 	; 24/03/2016, 25/03/2016, 28/03/2016
  3031                              <1> 	; 21/03/2016, 22/03/2016, 23/03/2016
  3032                              <1> 	; 16/03/2016, 17/03/2016, 18/03/2016
  3033                              <1> 	; 15/03/2016 (TRDOS 386 = TRDOS v2.0)
  3034                              <1> 	; 02/09/2011 (FILE.ASM 'copy_source_file_to_destination_file')
  3035                              <1> 	; 01/08/2010 - 18/05/2011
  3036                              <1> 	;
  3037                              <1> 	;   Command Interpreter phase 1 enter ->
  3038                              <1> 	;           AL = 1 -> Caller is command interpreter
  3039                              <1> 	;           AL = 2 -> The second call, re-enter/continue
  3040                              <1> 	;   Phase 1 -> Check source file
  3041                              <1> 	;              'found' is required
  3042                              <1> 	;   Phase 2 -> Check destination file, 
  3043                              <1> 	;              save 'found' or 'not found' status
  3044                              <1> 	;              'permission denied' error will be return
  3045                              <1> 	;              if attributes have not for ordinary file 
  3046                              <1> 	;              without readonly attribute
  3047                              <1> 	;   Command Interpreter phase 1 return ->
  3048                              <1> 	;              DH = Source file attributes
  3049                              <1> 	;              DL = Destination file found status
  3050                              <1> 	;              EAX = 0 
  3051                              <1> 	;   Command Interpreter phase 2 enter ->
  3052                              <1> 	;              AL = 2 -> Continue from the last position
  3053                              <1> 	;              AH = 
  3054                              <1> 	;   Phase 3 -> Load source file or use read/write cluster method
  3055                              <1> 	;   Phase 4 -> Create destination file if it is not found
  3056                              <1> 	;   Phase 5 -> Open destination file
  3057                              <1> 	;   Phase 6 -> Read from source and write to destination
  3058                              <1> 	;   Phase 7 -> Unload source file, if it is loaded at memory
  3059                              <1> 	;       cf = 1 causes to return before the phase 7
  3060                              <1> 	;              but loaded file will be unloaded
  3061                              <1> 	;	       (allocated memory block will be deallocated) 
  3062                              <1> 	;
  3063                              <1> 	; INPUT -> 
  3064                              <1> 	;	 ESI = Source File Pathname (Asciiz)
  3065                              <1> 	;        EDI = Destination File Pathname (Asciiz)
  3066                              <1> 	;        AL = 0 --> Interrupt (System call)
  3067                              <1> 	;        AL > 0 --> Command Interpreter (Question)
  3068                              <1> 	;        AL = 1 --> Question Phase
  3069                              <1> 	;        AL = 2 --> Progress Phase        
  3070                              <1> 	;
  3071                              <1> 	; OUTPUT -> 
  3072                              <1> 	;	cf = 0 -> OK
  3073                              <1> 	;	EAX = Destination file first cluster
  3074                              <1> 	;
  3075                              <1> 	;        CL > 0 if there is file reading error before EOF
  3076                              <1> 	;	        (incomplete copy) 
  3077                              <1> 	;        CH > 0 if file is (full) loaded at memory
  3078                              <1> 	;
  3079                              <1> 	;	cf = 1 -> Error code in AL (EAX) 
  3080                              <1> 	;
  3081                              <1> 	; (EBX, ECX, ESI, EDI register contents will be changed)           
  3082                              <1> 
  3083                              <1> 
  3084 0000B851 3C02                <1> 	cmp	al, 2
  3085 0000B853 0F845A020000        <1> 	je	csftdf2_check_cdrv
  3086                              <1> 
  3087                              <1> ; Phase 1
  3088                              <1> 
  3089 0000B859 A2[546A0100]        <1> 	mov	byte [copy_cmd_phase], al
  3090                              <1> 
  3091 0000B85E 57                  <1> 	push	edi ; *
  3092                              <1> 
  3093                              <1> csftdf_parse_sf_path:
  3094 0000B85F BF[2C690100]        <1> 	mov	edi, SourceFile_Drv
  3095 0000B864 E887F4FFFF          <1> 	call	parse_path_name
  3096 0000B869 721C                <1> 	jc	short csftdf_parse_sf_path_failed
  3097                              <1> 
  3098                              <1> csftdf_parse_df_path:	
  3099 0000B86B 5E                  <1> 	pop	esi ; * (pushed edi) 
  3100                              <1> 
  3101                              <1> csftdf_sf_check_filename_exists:
  3102 0000B86C 803D[6E690100]21    <1> 	cmp	byte [SourceFile_Name], 21h
  3103 0000B873 7215                <1> 	jb	short csftdf_sf_file_not_found_error
  3104                              <1> 
  3105 0000B875 BF[AC690100]        <1> 	mov	edi, DestinationFile_Drv
  3106 0000B87A E871F4FFFF          <1> 	call	parse_path_name
  3107 0000B87F 7310                <1> 	jnc	short csftdf_check_sf_cdrv
  3108                              <1> 	
  3109 0000B881 3C01                <1> 	cmp	al, 1 ; File or directory name is not existing
  3110 0000B883 760C                <1> 	jna	short csftdf_check_sf_cdrv
  3111                              <1> 
  3112                              <1> csftdf_parse_df_path_failed:
  3113 0000B885 F9                  <1> 	stc 
  3114                              <1> csftdf_sf_error_retn: 
  3115 0000B886 C3                  <1> 	retn
  3116                              <1> 
  3117                              <1> csftdf_parse_sf_path_failed:	
  3118 0000B887 5F                  <1> 	pop	edi ; *
  3119 0000B888 EBFC                <1> 	jmp	short csftdf_sf_error_retn
  3120                              <1> 
  3121                              <1> csftdf_sf_file_not_found_error:
  3122 0000B88A B802000000          <1> 	mov	eax, 2 ; File not found 
  3123 0000B88F EBF5                <1> 	jmp	short csftdf_sf_error_retn
  3124                              <1> 
  3125                              <1> csftdf_check_sf_cdrv:
  3126 0000B891 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  3127                              <1> 
  3128 0000B897 883D[576A0100]      <1> 	mov	[csftdf_cdrv], bh ; 23/03/2016
  3129                              <1> 
  3130 0000B89D 8A15[2C690100]      <1> 	mov	dl, [SourceFile_Drv]
  3131 0000B8A3 38FA                <1> 	cmp	dl, bh ; byte [Current_Drv]
  3132 0000B8A5 7407                <1> 	je	short csftdf_sf_check_directory
  3133                              <1> 
  3134 0000B8A7 E8D0BEFFFF          <1> 	call	change_current_drive
  3135 0000B8AC 72D8                <1> 	jc	short csftdf_sf_error_retn
  3136                              <1> 
  3137                              <1> csftdf_sf_check_directory:
  3138 0000B8AE BE[2D690100]        <1> 	mov	esi, SourceFile_Directory
  3139 0000B8B3 803E20              <1> 	cmp	byte [esi], 20h
  3140 0000B8B6 760F                <1> 	jna	short csftdf_find_sf
  3141                              <1> 
  3142                              <1> csftdf_sf_change_directory:
  3143 0000B8B8 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3144 0000B8BE 30E4                <1> 	xor	ah, ah ; CD_COMMAND sign -> 0 
  3145 0000B8C0 E815EEFFFF          <1> 	call	change_current_directory
  3146 0000B8C5 72BF                <1> 	jc	short csftdf_sf_error_retn
  3147                              <1> 
  3148                              <1> ;csftdf_sf_change_prompt_dir_string:
  3149                              <1> ;	call	change_prompt_dir_string
  3150                              <1> 
  3151                              <1> csftdf_find_sf:
  3152 0000B8C7 BE[6E690100]        <1> 	mov	esi, SourceFile_Name
  3153 0000B8CC 66B80018            <1> 	mov	ax, 1800h ; Except volume label and dirs
  3154 0000B8D0 E84AD2FFFF          <1> 	call	find_first_file
  3155 0000B8D5 72AF                <1> 	jc	short csftdf_sf_error_retn
  3156                              <1> 
  3157                              <1> csftdf_sf_ambgfn_check:
  3158 0000B8D7 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  3159 0000B8DA 7407                <1> 	jz	short csftdf_sf_found
  3160                              <1> 
  3161                              <1> csftdf_ambiguous_file_name_error:
  3162 0000B8DC B802000000          <1> 	mov	eax, 2 ; File not found error
  3163 0000B8E1 F9                  <1> 	stc
  3164 0000B8E2 C3                  <1> 	retn
  3165                              <1> 
  3166                              <1> csftdf_sf_found:
  3167 0000B8E3 A3[586A0100]        <1> 	mov	[csftdf_filesize], eax
  3168                              <1> 
  3169 0000B8E8 09C0                <1> 	or	eax, eax
  3170 0000B8EA 7507                <1> 	jnz	short csftdf_set_source_file_direntry
  3171                              <1> 
  3172                              <1> csftdf_sf_file_size_zero:
  3173 0000B8EC B814000000          <1> 	mov	eax, 20 ; TRDOS zero length (file size) error
  3174 0000B8F1 F9                  <1> 	stc
  3175 0000B8F2 C3                  <1> 	retn
  3176                              <1> 
  3177                              <1> csftdf_set_source_file_direntry:
  3178 0000B8F3 BE[38680100]        <1> 	mov	esi, FindFile_DirEntry
  3179 0000B8F8 BF[7E690100]        <1> 	mov	edi, SourceFile_DirEntry
  3180 0000B8FD B908000000          <1> 	mov	ecx, 8
  3181 0000B902 F3A5                <1> 	rep	movsd
  3182                              <1> 
  3183                              <1> csftdf_sf_restore_cdrv:
  3184                              <1> 	; 22/03/2016
  3185 0000B904 8A15[576A0100]      <1> 	mov	dl, [csftdf_cdrv]
  3186 0000B90A 3A15[465F0100]      <1> 	cmp	dl, [Current_Drv]
  3187 0000B910 7407                <1> 	je	short csftdf_sf_restore_cdir
  3188 0000B912 E865BEFFFF          <1> 	call	change_current_drive 
  3189 0000B917 724F                <1> 	jc	short csftdf_df_error_retn ; 30/03/2016
  3190                              <1> 
  3191                              <1> csftdf_sf_restore_cdir:
  3192 0000B919 803D[C7120100]00    <1> 	cmp	byte [Restore_CDIR], 0
  3193 0000B920 7612                <1> 	jna	short csftdf_df_check_filename_exists
  3194 0000B922 29C0                <1> 	sub	eax, eax
  3195 0000B924 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  3196 0000B929 88D4                <1> 	mov	ah, dl ; byte [csftdf_cdrv]
  3197 0000B92B 01C6                <1> 	add	esi, eax
  3198 0000B92D E801BFFFFF          <1> 	call	restore_current_directory
  3199 0000B932 7234                <1> 	jc	short csftdf_df_error_retn
  3200                              <1>   
  3201                              <1> csftdf_df_check_filename_exists:
  3202 0000B934 803D[EE690100]20    <1> 	cmp	byte [DestinationFile_Name], 20h
  3203 0000B93B 7716                <1> 	ja	short csftdf_check_df_cdrv
  3204                              <1> 
  3205                              <1> csftdf_copy_sf_name:
  3206 0000B93D BF[EE690100]        <1> 	mov	edi, DestinationFile_Name
  3207 0000B942 BE[6E690100]        <1> 	mov	esi, SourceFile_Name
  3208 0000B947 B10C                <1> 	mov	cl, 12
  3209                              <1> 
  3210                              <1> csftdf_df_copy_sf_name_loop:
  3211 0000B949 AC                  <1> 	lodsb
  3212 0000B94A AA                  <1> 	stosb
  3213 0000B94B 08C0                <1> 	or	al, al
  3214 0000B94D 7404                <1> 	jz	short csftdf_check_df_cdrv             
  3215 0000B94F FEC9                <1> 	dec	cl
  3216 0000B951 75F6                <1> 	jnz	csftdf_df_copy_sf_name_loop
  3217                              <1> 
  3218                              <1> csftdf_check_df_cdrv:
  3219 0000B953 8A15[AC690100]      <1> 	mov	dl, [DestinationFile_Drv]
  3220 0000B959 3A15[465F0100]      <1> 	cmp	dl, [Current_Drv]
  3221 0000B95F 7408                <1> 	je	short csftdf_df_check_directory
  3222                              <1> 
  3223 0000B961 E816BEFFFF          <1> 	call	change_current_drive
  3224 0000B966 7301                <1> 	jnc	short csftdf_df_check_directory
  3225                              <1> 
  3226                              <1> csftdf_df_error_retn:
  3227 0000B968 C3                  <1> 	retn
  3228                              <1> 
  3229                              <1> csftdf_df_check_directory:
  3230 0000B969 BE[AD690100]        <1> 	mov	esi, DestinationFile_Directory
  3231 0000B96E 803E20              <1>         cmp     byte [esi], 20h
  3232 0000B971 760F                <1> 	jna	short csftdf_find_df
  3233                              <1> 
  3234                              <1> csftdf_df_change_directory:
  3235 0000B973 FE05[C7120100]      <1> 	inc	byte [Restore_CDIR]
  3236 0000B979 28E4                <1> 	sub	ah, ah ; CD_COMMAND sign -> 0 
  3237 0000B97B E85AEDFFFF          <1> 	call	change_current_directory
  3238 0000B980 72E6                <1> 	jc	short csftdf_df_error_retn
  3239                              <1> 
  3240                              <1> ;csftdf_df_change_prompt_dir_string:
  3241                              <1> ;	call	change_prompt_dir_string
  3242                              <1> 
  3243                              <1> csftdf_find_df:
  3244                              <1> 	; 23/03/2016
  3245 0000B982 29DB                <1> 	sub	ebx, ebx
  3246 0000B984 8A3D[AC690100]      <1> 	mov	bh,  [DestinationFile_Drv]
  3247 0000B98A 81C300010900        <1> 	add	ebx, Logical_DOSDisks
  3248 0000B990 891D[846A0100]      <1> 	mov	[csftdf_df_drv_dt], ebx
  3249                              <1> 
  3250 0000B996 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  3251 0000B99B 6631C0              <1> 	xor	ax, ax 
  3252                              <1> 		; DestinationFile_AttributesMask -> any/zero
  3253 0000B99E E87CD1FFFF          <1> 	call	find_first_file
  3254 0000B9A3 7218                <1> 	jc	short csftdf_df_check_error_code
  3255                              <1> 
  3256                              <1> csftdf_df_ambgfn_check:
  3257 0000B9A5 6609D2              <1> 	or	dx, dx ; Ambiguous filename chars used sign (DX>0)
  3258 0000B9A8 752A                <1> 	jnz	short csftdf_df_error_inv_fname
  3259                              <1> 	
  3260                              <1> csftdf_df_found:
  3261 0000B9AA C605[566A0100]01    <1> 	mov	byte [DestinationFileFound], 1
  3262                              <1> 	; 17/10/2016 (cl -> bl)
  3263 0000B9B1 80E31F              <1> 	and	bl, 1Fh ; Attributes, D-V-S-H-R
  3264 0000B9B4 745F                <1> 	jz	short csftdf_df_save_first_cluster
  3265                              <1> 
  3266                              <1> csftdf_df_permission_denied_retn:	 
  3267 0000B9B6 B805000000          <1> 	mov	eax, 05h ; Access/Permission denied.
  3268                              <1> csftdf_df_error_stc_retn:
  3269 0000B9BB F9                  <1> 	stc
  3270 0000B9BC C3                  <1> 	retn
  3271                              <1> 
  3272                              <1> csftdf_df_check_error_code:
  3273                              <1> 	;cmp	eax, 2
  3274 0000B9BD 3C02                <1> 	cmp	al, 2
  3275 0000B9BF 75FA                <1> 	jne	short csftdf_df_error_stc_retn
  3276                              <1> 
  3277 0000B9C1 C605[566A0100]00    <1> 	mov	byte [DestinationFileFound], 0
  3278                              <1> 
  3279                              <1> 	; 15/10/2016
  3280 0000B9C8 BE[28680100]        <1> 	mov	esi, FindFile_Name ; *
  3281 0000B9CD E80BD5FFFF          <1> 	call	check_filename
  3282 0000B9D2 7307                <1> 	jnc	short csftdf_df_valid_fname
  3283                              <1> csftdf_df_error_inv_fname: ; 'invalid file name !'
  3284 0000B9D4 B81A000000          <1> 	mov 	eax, ERR_INV_FILE_NAME  ; 26
  3285 0000B9D9 F9                  <1> 	stc	
  3286 0000B9DA C3                  <1> 	retn
  3287                              <1> 
  3288                              <1> csftdf_df_valid_fname:	
  3289                              <1> 	; 21/03/2016
  3290                              <1> 	; (Capitalized file name)
  3291                              <1> 	;mov	esi, FindFile_Name ; * ; 15/10/2016
  3292 0000B9DB BF[EE690100]        <1> 	mov	edi, DestinationFile_Name
  3293 0000B9E0 A5                  <1> 	movsd
  3294 0000B9E1 A5                  <1> 	movsd	
  3295 0000B9E2 A5                  <1> 	movsd
  3296                              <1> 	;movsb
  3297                              <1> 
  3298                              <1> csftdf_check_disk_free_size_0:
  3299 0000B9E3 A1[9A690100]        <1> 	mov	eax, [SourceFile_DirEntry+DirEntry_FileSize]
  3300                              <1> 
  3301                              <1> csftdf_check_disk_free_size_1:
  3302                              <1> 	;sub	ebx, ebx
  3303                              <1> 	;mov 	esi, Logical_DOSDisks
  3304                              <1> 	;mov	bh,  [DestinationFile_Drv]
  3305                              <1> 	;add	esi, ebx
  3306                              <1> 	
  3307 0000B9E8 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt] ; 23/03/2016
  3308                              <1> 
  3309 0000B9EE 0FB74E11            <1> 	movzx	ecx, word [esi+LD_BPB+BytesPerSec] ; 17, LD_BPB + 0Bh
  3310 0000B9F2 01C8                <1> 	add	eax, ecx
  3311 0000B9F4 48                  <1> 	dec	eax  ; file size (additional bytes) + 511 (round up)
  3312                              <1> csftdf_check_disk_free_size_3: ; 16/03/2016
  3313 0000B9F5 29D2                <1> 	sub	edx, edx
  3314 0000B9F7 F7F1                <1> 	div	ecx ; bytes per sector
  3315                              <1> 
  3316                              <1> csftdf_check_disk_free_size:
  3317 0000B9F9 3B4674              <1> 	cmp	eax, [esi+LD_FreeSectors]
  3318 0000B9FC 0F8294000000        <1>         jb      csftdf_check_disk_free_size_ok
  3319 0000BA02 770A                <1> 	ja	short csftdf_df_insufficient_disk_space
  3320                              <1> 
  3321 0000BA04 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0 ; FS needs FDT sector also.
  3322 0000BA08 0F8788000000        <1>         ja      csftdf_check_disk_free_size_ok 
  3323                              <1> 
  3324                              <1> csftdf_df_insufficient_disk_space:
  3325 0000BA0E B827000000          <1> 	mov	eax, 27h ; insufficient disk space
  3326 0000BA13 EBA6                <1> 	jmp	short csftdf_df_error_stc_retn
  3327                              <1> 
  3328                              <1> csftdf_df_save_first_cluster:
  3329                              <1> 	; ESI = FindFile_DirEntry (for the old destination file)
  3330                              <1> 	; EAX = Old destination file size
  3331                              <1> 	; 24/03/2016
  3332                              <1> 	; EDI = Directory entry address (within Dir Buffer boundaries)
  3333 0000BA15 81EF00000800        <1> 	sub	edi, Directory_Buffer  ; (<65536)
  3334 0000BA1B 66C1EF05            <1> 	shr	di, 5 ; Convert entry offset to entry index/number
  3335 0000BA1F 66893D[266A0100]    <1> 	mov	[DestinationFile_DirEntryNumber], di ; (<2048)
  3336                              <1> 
  3337                              <1> csftdf_df_check_sf_df_fcluster:
  3338 0000BA26 668B5614            <1> 	mov	dx, [esi+DirEntry_FstClusHI]
  3339 0000BA2A C1E210              <1> 	shl	edx, 16
  3340 0000BA2D 668B561A            <1> 	mov	dx, [esi+DirEntry_FstClusLO]
  3341 0000BA31 8915[686A0100]      <1> 	mov	[csftdf_df_cluster], edx
  3342                              <1> csftdf_df_check_sf_df_fcluster_1:
  3343 0000BA37 668B15[92690100]    <1> 	mov	dx, [SourceFile_DirEntry+DirEntry_FstClusHI]
  3344 0000BA3E C1E210              <1> 	shl	edx, 16
  3345 0000BA41 668B15[98690100]    <1> 	mov	dx, [SourceFile_DirEntry+DirEntry_FstClusLO]
  3346 0000BA48 3B15[686A0100]      <1> 	cmp	edx, [csftdf_df_cluster]
  3347 0000BA4E 7512                <1> 	jne	short csftdf_df_check_sf_df_fcluster_ok
  3348                              <1> csftdf_df_check_sf_df_drv:
  3349 0000BA50 8A15[2C690100]      <1> 	mov	dl, [SourceFile_Drv]
  3350 0000BA56 3A15[AC690100]      <1> 	cmp	dl, [DestinationFile_Drv]
  3351 0000BA5C 7504                <1> 	jne	short csftdf_df_check_sf_df_fcluster_ok
  3352                              <1> 
  3353                              <1> 	; source and destination files are same !
  3354                              <1> 	; (they have same first cluster value on same logical disk)
  3355                              <1> 
  3356 0000BA5E 31C0                <1> 	xor	eax, eax ; mov eax, 0 -> Bad command or file name !
  3357 0000BA60 F9                  <1> 	stc
  3358 0000BA61 C3                  <1> 	retn 
  3359                              <1>    
  3360                              <1> csftdf_df_check_sf_df_fcluster_ok:
  3361                              <1> csftdf_df_move_findfile_struct:
  3362                              <1> 	; mov	esi, FindFile_DirEntry
  3363 0000BA62 BF[FE690100]        <1> 	mov	edi, DestinationFile_DirEntry
  3364 0000BA67 B908000000          <1> 	mov	ecx, 8
  3365 0000BA6C F3A5                <1> 	rep	movsd
  3366                              <1> 	
  3367                              <1> csftdf_check_disk_free_size_2:
  3368 0000BA6E 89C2                <1> 	mov	edx, eax ; Old destination file size
  3369                              <1> 
  3370                              <1> 	;mov	eax, [SourceFile_DirEntry+DirEntry_FileSize]
  3371 0000BA70 A1[586A0100]        <1> 	mov	eax, [csftdf_filesize] ; 23/03/2016
  3372                              <1> 
  3373                              <1> 	;;sub	ecx, ecx ; 0
  3374                              <1> 	;mov 	esi, Logical_DOSDisks
  3375                              <1> 	;mov	ch,  [DestinationFile_Drv]
  3376                              <1> 	;add	esi, ecx
  3377                              <1> 	;
  3378                              <1> 	;mov	[csftdf_df_drv_dt], esi
  3379                              <1> 
  3380 0000BA75 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt] ; 23/03/2016
  3381                              <1> 
  3382 0000BA7B 668B4E11            <1> 	mov	cx, [esi+LD_BPB+BytesPerSec] ; 17, LD_BPB + 0Bh
  3383 0000BA7F 01CA                <1> 	add	edx, ecx ; + 512
  3384 0000BA81 01C8                <1> 	add	eax, ecx ; + 512
  3385 0000BA83 4A                  <1> 	dec	edx ; old file size + 511 (round up)
  3386 0000BA84 48                  <1> 	dec	eax ; new file size + 511 (round up)
  3387 0000BA85 F7D9                <1> 	neg	ecx ; -512 ; 0FFFFFE00h
  3388 0000BA87 21CA                <1> 	and	edx, ecx ; = old sector count * 512 
  3389 0000BA89 21C8                <1> 	and	eax, ecx ; = new sector count * 512 
  3390                              <1> 
  3391 0000BA8B 29D0                <1> 	sub	eax, edx ; new file size - old file size (on disk)
  3392 0000BA8D 7607                <1> 	jna	short csftdf_check_disk_free_size_ok
  3393                              <1> 
  3394 0000BA8F F7D9                <1> 	neg	ecx ; 512 (bytes per sector) ; 200h
  3395                              <1> 	; check free space for additional sectors
  3396                              <1> 	; eax = number of additional sectors * bytes per sector
  3397                              <1> 	; esi = Logical DOS drive number (of destination disk)
  3398 0000BA91 E95FFFFFFF          <1>         jmp     csftdf_check_disk_free_size_3
  3399                              <1>  
  3400                              <1> csftdf_check_disk_free_size_ok:
  3401                              <1> 	; 18/03/2016
  3402                              <1> csftdf_df_check_copy_cmd_phase:
  3403 0000BA96 A0[546A0100]        <1> 	mov	al, [copy_cmd_phase]
  3404 0000BA9B 3C01                <1> 	cmp	al, 1
  3405 0000BA9D 7514                <1> 	jne	short csftdf2_check_cdrv
  3406                              <1> 	
  3407 0000BA9F 31C0                <1> 	xor	eax, eax
  3408 0000BAA1 A2[546A0100]        <1> 	mov	[copy_cmd_phase], al ; 0
  3409                              <1> 
  3410 0000BAA6 8A15[566A0100]      <1> 	mov	dl, [DestinationFileFound]            
  3411 0000BAAC 8A35[89690100]      <1> 	mov	dh, [SourceFile_DirEntry+11] ; Attributes
  3412                              <1>  
  3413                              <1> csftdf_return:	
  3414 0000BAB2 C3                  <1> 	retn
  3415                              <1> 
  3416                              <1> ; Phase 2
  3417                              <1> 
  3418                              <1> csftdf2_check_cdrv:
  3419                              <1> 	; 18/03/2016
  3420                              <1> 	; Here, destination drive and directory are ready !
  3421                              <1> 	; (checking/restoring is not needed)
  3422                              <1> 	; (Since at the end of the phase 1)
  3423                              <1> 
  3424                              <1> ;	mov	dl, [DestinationFile_Drv]
  3425                              <1> ;	cmp	dl, [Current_Drv]
  3426                              <1> ;	je	short csftdf2_df_check_directory
  3427                              <1> ;
  3428                              <1> ;	call	change_current_drive
  3429                              <1> ;	jc	short csftdf2_read_error
  3430                              <1> ;
  3431                              <1> ;csftdf2_df_check_directory:
  3432                              <1> ;	mov	esi, DestinationFile_Directory  
  3433                              <1> ;	cmp	byte [esi], 20h
  3434                              <1> ;	jna	short csftdf2_df_check_found_or_not
  3435                              <1> ;
  3436                              <1> ;csftdf2_df_change_directory:
  3437                              <1> ;	inc	byte [Restore_CDIR]
  3438                              <1> ;	xor	ah, ah ; CD_COMMAND sign -> 0 
  3439                              <1> ;	call	change_current_directory
  3440                              <1> ;	jc	short csftdf2_stc_return
  3441                              <1> ;
  3442                              <1> ;;csftdf2_df_change_prompt_dir_string:
  3443                              <1> ;;	call	change_prompt_dir_string
  3444                              <1> 
  3445                              <1> csftdf2_df_check_found_or_not:
  3446                              <1> 	; 21/03/2016
  3447 0000BAB3 803D[566A0100]00    <1> 	cmp	byte [DestinationFileFound], 0 
  3448 0000BABA 7739                <1> 	ja	short csftdf2_set_sf_percentage
  3449                              <1> 
  3450                              <1> csftdf2_create_file:
  3451 0000BABC BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  3452 0000BAC1 A1[586A0100]        <1> 	mov	eax, [csftdf_filesize]
  3453 0000BAC6 30C9                <1> 	xor	cl, cl ; 0
  3454                              <1> 
  3455 0000BAC8 31DB                <1> 	xor	ebx, ebx ; 0
  3456 0000BACA 4B                  <1> 	dec	ebx ; 0FFFFFFFFh 
  3457                              <1> 
  3458                              <1> 	; INPUT ->
  3459                              <1> 	; 	EAX -> File Size
  3460                              <1> 	; 	ESI = ASCIIZ File name
  3461                              <1> 	;	 CL = File attributes
  3462                              <1> 	;	EBX = FFFFFFFFh -> empty file sign for FAT fs
  3463                              <1> 	;	EBX <> FFFFFFFFh -> use file size for FAT fs 
  3464                              <1> 	;
  3465                              <1> 	; OUTPUT ->
  3466                              <1> 	;	EAX = New file's first cluster
  3467                              <1> 	;	ESI = Logical Dos Drv Descr. Table Addr.
  3468                              <1> 	;	EBX = CreateFile_Size address
  3469                              <1> 	;	ECX = Sectors per cluster (<256)
  3470                              <1> 	;	EDX = Directory Entry Index/Number (<65536)
  3471                              <1> 	;		
  3472                              <1> 	;	cf = 1 -> error code in AL (EAX)
  3473                              <1> 
  3474 0000BACB E8EC050000          <1> 	call	create_file
  3475                              <1> 	;pop	esi
  3476 0000BAD0 0F82A3050000        <1>         jc      csftdf2_rw_error
  3477                              <1> 
  3478                              <1> csftdf2_create_file_OK:
  3479 0000BAD6 A3[686A0100]        <1> 	mov	[csftdf_df_cluster], eax
  3480                              <1> 	
  3481                              <1> 	; 24/03/2016
  3482 0000BADB 668915[266A0100]    <1> 	mov	[DestinationFile_DirEntryNumber], dx 
  3483                              <1> 
  3484                              <1> 	; 21/03/2016
  3485 0000BAE2 BE00000800          <1> 	mov	esi, Directory_Buffer
  3486 0000BAE7 C1E205              <1> 	shl	edx, 5 ; 32 * index number
  3487 0000BAEA 01D6                <1> 	add	esi, edx
  3488 0000BAEC BF[FE690100]        <1> 	mov	edi, DestinationFile_DirEntry	
  3489 0000BAF1 B108                <1> 	mov	cl, 8 ; 32 bytes
  3490 0000BAF3 F3A5                <1> 	rep	movsd
  3491                              <1> 
  3492                              <1> csftdf2_set_sf_percentage:
  3493                              <1> 	; 17/03/2016
  3494 0000BAF5 31C0                <1> 	xor	eax, eax	
  3495 0000BAF7 A2[7C6A0100]        <1> 	mov 	[csftdf_percentage], al ; 0, reset
  3496                              <1> 
  3497 0000BAFC A3[746A0100]        <1> 	mov	[csftdf_sf_rbytes], eax ; 0, reset
  3498 0000BB01 A3[786A0100]        <1> 	mov	[csftdf_df_wbytes], eax ; 0, reset
  3499                              <1> 
  3500 0000BB06 8A25[2C690100]      <1> 	mov	ah, [SourceFile_Drv]	
  3501 0000BB0C BE00010900          <1> 	mov	esi, Logical_DOSDisks
  3502 0000BB11 01C6                <1> 	add	esi, eax
  3503                              <1> 	
  3504 0000BB13 8935[806A0100]      <1> 	mov	[csftdf_sf_drv_dt], esi ; 23/03/2016
  3505                              <1> 
  3506 0000BB19 668B15[92690100]    <1> 	mov	dx, [SourceFile_DirEntry+DirEntry_FstClusHI]
  3507 0000BB20 C1E210              <1> 	shl	edx, 16
  3508 0000BB23 668B15[98690100]    <1> 	mov	dx, [SourceFile_DirEntry+DirEntry_FstClusLO]
  3509 0000BB2A 8915[646A0100]      <1> 	mov	[csftdf_sf_cluster], edx
  3510                              <1> 
  3511                              <1> 	; 16/03/2016
  3512                              <1> 	; Note: Singlix FS boot sector parameters (for cluster
  3513                              <1> 	;	related calculations) has same offset
  3514                              <1> 	;	values from LD_BPB as in FAT file system.
  3515                              <1> 	;	[esi+LD_BPB+SecPerClust] is 1 for Singlix FS.
  3516                              <1> 	;	
  3517 0000BB30 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+SecPerClust]
  3518 0000BB34 880D[AA690100]      <1> 	mov	[SourceFile_SecPerClust], cl
  3519                              <1> 
  3520                              <1> 	; 17/03/2016
  3521 0000BB3A 386E03              <1> 	cmp	[esi+LD_FATType], ch ; 0
  3522 0000BB3D 7707                <1> 	ja	short csftdf2_set_sf_percent_rsize1
  3523                              <1> 
  3524 0000BB3F B800000100          <1> 	mov	eax, 65536 ; read/write buffer size for Singlix FS
  3525 0000BB44 EB06                <1> 	jmp	short csftdf2_set_sf_percent_rsize2	
  3526                              <1>  
  3527                              <1> csftdf2_set_sf_percent_rsize1:
  3528 0000BB46 668B4611            <1> 	mov	ax, [esi+LD_BPB+BytesPerSec]
  3529 0000BB4A F7E1                <1> 	mul	ecx
  3530                              <1> 	;sub	edx, edx
  3531                              <1> csftdf2_set_sf_percent_rsize2:
  3532 0000BB4C A3[6C6A0100]        <1> 	mov	[csftdf_r_size], eax
  3533                              <1> 
  3534                              <1> csftdf2_set_df_percentage:
  3535                              <1> 	;sub	eax, eax
  3536                              <1> 	;mov	ah, [DestinationFile_Drv]	
  3537                              <1> 	;mov	edi, Logical_DOSDisks
  3538                              <1> 	;add	edi, eax
  3539                              <1> 	;mov	[csftdf_df_drv_dt], edi ; 17/03/2016
  3540                              <1> 
  3541 0000BB51 8B3D[846A0100]      <1> 	mov	edi, [csftdf_df_drv_dt] ; 23/03/2016
  3542                              <1> 
  3543                              <1> 	; 16/03/2016
  3544                              <1> 	; Note: Singlix FS boot sector parameters (for cluster
  3545                              <1> 	;	related calculations) has same offset
  3546                              <1> 	;	values from LD_BPB as in FAT file system.
  3547                              <1> 	;	[edi+LD_BPB+SecPerClust] is 1 for Singlix FS.
  3548                              <1> 	;	
  3549                              <1> 	;movzx	ecx, byte [edi+LD_BPB+SecPerClust]
  3550 0000BB57 8A4F13              <1> 	mov	cl, [edi+LD_BPB+SecPerClust]
  3551 0000BB5A 880D[2A6A0100]      <1> 	mov	[DestinationFile_SecPerClust], cl
  3552                              <1> 
  3553                              <1> 	; 17/03/2016
  3554 0000BB60 386F03              <1> 	cmp	[edi+LD_FATType], ch ; 0
  3555 0000BB63 7707                <1> 	ja	short csftdf2_set_df_percent_wsize1
  3556                              <1> 	
  3557 0000BB65 B800000100          <1> 	mov	eax, 65536 ; read/write buffer size for Singlix FS
  3558 0000BB6A EB06                <1> 	jmp	short csftdf2_set_df_percent_wsize2	
  3559                              <1> 
  3560                              <1> csftdf2_set_df_percent_wsize1:
  3561 0000BB6C 0FB74711            <1> 	movzx	eax, word [edi+LD_BPB+BytesPerSec]
  3562 0000BB70 F7E1                <1> 	mul	ecx
  3563                              <1> 	;sub	edx, edx
  3564                              <1> csftdf2_set_df_percent_wsize2:
  3565 0000BB72 A3[706A0100]        <1> 	mov	[csftdf_w_size], eax
  3566                              <1> 
  3567 0000BB77 A1[586A0100]        <1> 	mov	eax, [csftdf_filesize]
  3568                              <1> 
  3569 0000BB7C 3D00000100          <1> 	cmp	eax, 65536 ; 64KB	; small file
  3570 0000BB81 721F                <1> 	jb	short csftdf2_load_file ; do not display percentage
  3571                              <1> 	
  3572                              <1> csftdf2_reset_wf_percent_ptr_chk_64k:
  3573 0000BB83 B201                <1> 	mov	dl, 1 ; 25/03/2016
  3574                              <1> 
  3575 0000BB85 3D00000400          <1> 	cmp	eax, 65536*4 ; 256KB
  3576 0000BB8A 7310                <1> 	jnb	short csftdf2_enable_percentage_display ; big file
  3577                              <1> 
  3578                              <1> 	; 64-128KB file size for floppy disks
  3579 0000BB8C 3815[2C690100]      <1> 	cmp	byte [SourceFile_Drv], dl ; 1 ; read from floppy disk ?
  3580 0000BB92 7608                <1> 	jna	short csftdf2_enable_percentage_display
  3581                              <1> 
  3582 0000BB94 3815[AC690100]      <1> 	cmp	byte [DestinationFile_Drv], dl ; 1 ; write to floppy disk ?
  3583 0000BB9A 7706                <1> 	ja	short csftdf2_load_file
  3584                              <1> 
  3585                              <1> csftdf2_enable_percentage_display:	
  3586 0000BB9C 8815[7C6A0100]      <1> 	mov	[csftdf_percentage], dl ; 1	
  3587                              <1> 	
  3588                              <1> csftdf2_load_file:
  3589                              <1> 	; 13/05/2016
  3590                              <1> 	; 19/03/2016
  3591                              <1> 	; 18/03/2016
  3592                              <1> 	; 17/03/2016
  3593 0000BBA2 B40F                <1> 	mov	ah, 0Fh
  3594 0000BBA4 E8355BFFFF          <1> 	call	_int10h
  3595                              <1> 	; 13/05/2016
  3596 0000BBA9 883D[7D6A0100]      <1> 	mov	[csftdf_videopage], bh ; active video page
  3597 0000BBAF B403                <1> 	mov	ah, 03h
  3598 0000BBB1 E8285BFFFF          <1> 	call	_int10h
  3599 0000BBB6 668915[7E6A0100]    <1> 	mov	[csftdf_cursorpos], dx
  3600                              <1> 
  3601 0000BBBD 29C0                <1> 	sub	eax, eax
  3602 0000BBBF A2[556A0100]        <1> 	mov	[csftdf_rw_err], al ; 0 
  3603                              <1> 
  3604                              <1> ; ///
  3605                              <1> csftdf_sf_amb: ; 15/03/2016
  3606 0000BBC4 8B0D[586A0100]      <1> 	mov	ecx, [csftdf_filesize]	; 23/03/2016
  3607                              <1> 
  3608                              <1> 	; TRDOS 386 (TRDOS v2.0)
  3609                              <1> 	; Allocate contiguous memory block for loading the file
  3610                              <1> 	
  3611                              <1> 	;mov	ecx, [SourceFile_DirEntry+DirEntry_FileSize]
  3612                              <1> 	
  3613                              <1> 	;sub	eax, eax ; First free memory aperture
  3614                              <1> 	
  3615                              <1> 	; eax = 0 (Allocate memory from the beginning)
  3616                              <1> 	; ecx = File (Allocation) size in bytes
  3617                              <1> 	
  3618 0000BBCA E8C09FFFFF          <1> 	call	allocate_memory_block
  3619 0000BBCF 7304                <1> 	jnc	short loc_check_sf_save_loading_parms
  3620                              <1> 
  3621 0000BBD1 29C0                <1> 	sub	eax, eax
  3622 0000BBD3 29C9                <1> 	sub	ecx, ecx
  3623                              <1> 	
  3624                              <1> loc_check_sf_save_loading_parms:
  3625 0000BBD5 A3[5C6A0100]        <1> 	mov	[csftdf_sf_mem_addr], eax ; loading address
  3626 0000BBDA 890D[606A0100]      <1> 	mov	[csftdf_sf_mem_bsize], ecx ; block size
  3627                              <1> ; ///   
  3628                              <1> 	; 19/03/2016
  3629 0000BBE0 8B35[806A0100]      <1> 	mov	esi, [csftdf_sf_drv_dt] ; logical dos drv desc. tbl.
  3630                              <1> 
  3631                              <1> 	; 17/03/2016
  3632 0000BBE6 09C0                <1> 	or	eax, eax ; contiguous free memory block address 
  3633 0000BBE8 0F845B010000        <1>         jz      csftdf2_read_sf_cluster
  3634                              <1> 
  3635                              <1> 	; 18/03/2016
  3636 0000BBEE 8B1D[5C6A0100]      <1> 	mov	ebx, [csftdf_sf_mem_addr] ; memory block address
  3637                              <1> 
  3638 0000BBF4 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  3639 0000BBF8 0F8605020000        <1>         jna     csftdf2_load_fs_file
  3640                              <1> 
  3641                              <1> csftdf2_load_fat_file:
  3642 0000BBFE 53                  <1> 	push	ebx ; *
  3643                              <1> 
  3644                              <1> csftdf2_load_fat_file_next:
  3645 0000BBFF BE[17190100]        <1> 	mov	esi, msg_reading
  3646 0000BC04 E8FCAFFFFF          <1> 	call	print_msg
  3647                              <1> 
  3648 0000BC09 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3649 0000BC10 7605                <1> 	jna	short csftdf2_load_fat_file_1
  3650                              <1> 	
  3651 0000BC12 E87C000000          <1> 	call	csftdf2_print_percentage ; 19/03/2016
  3652                              <1> 
  3653                              <1> csftdf2_load_fat_file_1:
  3654 0000BC17 8B35[806A0100]      <1> 	mov	esi, [csftdf_sf_drv_dt]	
  3655 0000BC1D 5B                  <1> 	pop	ebx ; *
  3656                              <1> 
  3657                              <1> csftdf2_load_fat_file_2:
  3658 0000BC1E E8B8000000          <1> 	call	csftdf2_read_fat_file_sectors ; 19/03/2016
  3659 0000BC23 0F8250040000        <1>         jc      csftdf2_rw_error ; eocc! or disk error! 
  3660                              <1> 
  3661 0000BC29 09D2                <1> 	or	edx, edx ; edx > 0 -> EOF
  3662 0000BC2B 7520                <1> 	jnz	short csftdf2_load_fat_file_ok
  3663                              <1> 
  3664 0000BC2D 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3665 0000BC34 76E8                <1> 	jna	short csftdf2_load_fat_file_2
  3666                              <1> 
  3667 0000BC36 53                  <1> 	push	ebx ; *	
  3668                              <1> 
  3669                              <1> 	; Set cursor position
  3670                              <1> 	; AH= 02h, BH= Page Number, DH= Row, DL= Column
  3671 0000BC37 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  3672 0000BC3D 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  3673 0000BC44 B402                <1> 	mov	ah, 2
  3674 0000BC46 E8935AFFFF          <1> 	call	_int10h
  3675 0000BC4B EBB2                <1> 	jmp	short csftdf2_load_fat_file_next
  3676                              <1> 	
  3677                              <1> csftdf2_load_fat_file_ok:
  3678 0000BC4D 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3679 0000BC54 0F8651020000        <1>         jna     csftdf2_save_file ; 25/03/2016
  3680                              <1> 	
  3681                              <1> 	; "Reading... 100%"
  3682 0000BC5A BF[2F190100]        <1> 	mov	edi, percentagestr
  3683 0000BC5F B031                <1> 	mov	al, '1'
  3684 0000BC61 AA                  <1> 	stosb
  3685 0000BC62 B030                <1> 	mov	al, '0'
  3686 0000BC64 AA                  <1> 	stosb
  3687 0000BC65 AA                  <1> 	stosb
  3688                              <1> 
  3689 0000BC66 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  3690 0000BC6C 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  3691 0000BC73 B402                <1> 	mov	ah, 2
  3692 0000BC75 E8645AFFFF          <1> 	call	_int10h
  3693                              <1> 
  3694 0000BC7A BE[17190100]        <1> 	mov	esi, msg_reading
  3695 0000BC7F E881AFFFFF          <1> 	call	print_msg
  3696                              <1> 	
  3697 0000BC84 BE[2F190100]        <1> 	mov	esi, percentagestr
  3698 0000BC89 E877AFFFFF          <1> 	call	print_msg
  3699                              <1> 
  3700 0000BC8E E918020000          <1>         jmp     csftdf2_save_file ; 25/03/2016
  3701                              <1> 
  3702                              <1> csftdf2_print_percentage:
  3703                              <1> 	; 09/12/2017
  3704                              <1> 	; 19/03/2016
  3705                              <1> 	; 18/03/2016
  3706 0000BC93 B020                <1> 	mov	al, 20h
  3707 0000BC95 BF[2F190100]        <1> 	mov	edi, percentagestr
  3708 0000BC9A AA                  <1> 	stosb
  3709 0000BC9B AA                  <1> 	stosb
  3710 0000BC9C A1[746A0100]        <1> 	mov	eax, [csftdf_sf_rbytes]
  3711 0000BCA1 BA64000000          <1> 	mov	edx, 100
  3712 0000BCA6 F7E2                <1> 	mul	edx
  3713 0000BCA8 8B0D[586A0100]      <1> 	mov	ecx, [csftdf_filesize]	
  3714 0000BCAE F7F1                <1> 	div	ecx
  3715 0000BCB0 B10A                <1> 	mov	cl, 10
  3716 0000BCB2 F6F1                <1> 	div	cl
  3717 0000BCB4 80C430              <1> 	add	ah, '0'
  3718 0000BCB7 8827                <1> 	mov	[edi], ah
  3719 0000BCB9 20C0                <1> 	and	al, al
  3720 0000BCBB 740A                <1> 	jz	short csftdf2_print_percent_1
  3721 0000BCBD 4F                  <1> 	dec	edi
  3722                              <1> 	;cbw
  3723 0000BCBE 28E4                <1> 	sub	ah, ah ; 09/12/2017
  3724 0000BCC0 F6F1                <1> 	div	cl
  3725 0000BCC2 80C430              <1> 	add	ah, '0'
  3726 0000BCC5 8827                <1> 	mov	[edi], ah
  3727                              <1> 	;and	al, al
  3728                              <1> 	;jz	short csftdf2_print_percent_1
  3729                              <1> 	;dec	edi
  3730                              <1> 	;mov	[edi], '1' ; 100%		
  3731                              <1> 
  3732                              <1> csftdf2_print_percent_1:
  3733 0000BCC7 BE[2F190100]        <1> 	mov	esi, percentagestr
  3734                              <1> 	;call	print_msg
  3735                              <1> 	;retn
  3736 0000BCCC E934AFFFFF          <1> 	jmp	print_msg
  3737                              <1> 
  3738                              <1> csftdf2_read_file_sectors:
  3739                              <1> 	; 19/03/2016
  3740 0000BCD1 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  3741 0000BCD5 0F8627070000        <1>         jna     csftdf2_read_fs_file_sectors
  3742                              <1> 
  3743                              <1> csftdf2_read_fat_file_sectors:
  3744                              <1> 	; 19/03/2016
  3745                              <1> 	; 18/03/2016
  3746                              <1> 	; return:
  3747                              <1> 	;   CF = 0 & EDX > 0 -> END OF FILE
  3748                              <1> 	;   CF = 0 & EDX = 0 -> not EOF
  3749                              <1> 	;   CF = 1 -> read error (error code in AL)	
  3750                              <1> 
  3751                              <1> csftdf2_read_fat_file_secs_0:
  3752 0000BCDB 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  3753 0000BCE1 2B15[746A0100]      <1> 	sub	edx, [csftdf_sf_rbytes]
  3754 0000BCE7 3B15[6C6A0100]      <1> 	cmp	edx, [csftdf_r_size]	
  3755 0000BCED 7306                <1> 	jnb	short csftdf2_read_fat_file_secs_1
  3756 0000BCEF 8915[6C6A0100]      <1> 	mov	[csftdf_r_size], edx
  3757                              <1> 		
  3758                              <1> csftdf2_read_fat_file_secs_1:
  3759 0000BCF5 A1[6C6A0100]        <1> 	mov	eax, [csftdf_r_size]
  3760 0000BCFA 29D2                <1> 	sub	edx, edx
  3761 0000BCFC 0FB74E11            <1> 	movzx	ecx, word [esi+LD_BPB+BytesPerSec]
  3762 0000BD00 01C8                <1> 	add	eax, ecx
  3763 0000BD02 48                  <1> 	dec	eax
  3764 0000BD03 F7F1                <1> 	div	ecx
  3765 0000BD05 89C1                <1> 	mov	ecx, eax ; sector count
  3766 0000BD07 A1[646A0100]        <1> 	mov	eax, [csftdf_sf_cluster]
  3767                              <1> 
  3768                              <1> 	; EBX = memory block address (current)
  3769                              <1> 	
  3770 0000BD0C E821090000          <1> 	call	read_fat_file_sectors
  3771 0000BD11 7235                <1> 	jc	short csftdf2_read_fat_file_secs_3
  3772                              <1> 
  3773                              <1> 	; EBX = next memory address
  3774                              <1> 
  3775 0000BD13 A1[746A0100]        <1> 	mov	eax, [csftdf_sf_rbytes]
  3776 0000BD18 0305[6C6A0100]      <1> 	add	eax, [csftdf_r_size]
  3777 0000BD1E 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  3778 0000BD24 39D0                <1> 	cmp	eax, edx
  3779 0000BD26 7320                <1> 	jnb	short csftdf2_read_fat_file_secs_3 ; edx > 0
  3780 0000BD28 A3[746A0100]        <1> 	mov	[csftdf_sf_rbytes], eax
  3781                              <1> 
  3782 0000BD2D 53                  <1> 	push	ebx ; *
  3783                              <1> 	; get next cluster (csftdf_r_size! bytes)
  3784 0000BD2E A1[646A0100]        <1> 	mov	eax, [csftdf_sf_cluster]
  3785 0000BD33 E8CC060000          <1> 	call	get_next_cluster
  3786 0000BD38 5B                  <1> 	pop	ebx ; *
  3787 0000BD39 7306                <1> 	jnc	short csftdf2_read_fat_file_secs_2
  3788                              <1> 
  3789                              <1> 	; 15/10/2016
  3790                              <1> 	;Disk read error instad of drv not ready err
  3791 0000BD3B B811000000          <1> 	mov	eax, 17 ; Read error !
  3792 0000BD40 C3                  <1> 	retn
  3793                              <1> 
  3794                              <1> csftdf2_read_fat_file_secs_2:
  3795 0000BD41 29D2                <1> 	sub	edx, edx ; 0
  3796 0000BD43 A3[646A0100]        <1> 	mov	[csftdf_sf_cluster], eax ; next cluster
  3797                              <1> 
  3798                              <1> csftdf2_read_fat_file_secs_3:
  3799 0000BD48 C3                  <1> 	retn
  3800                              <1> 
  3801                              <1> csftdf2_read_sf_cluster:
  3802                              <1> 	; 19/03/2016
  3803 0000BD49 BB00000700          <1> 	mov	ebx, Cluster_Buffer ; buffer address (64KB)
  3804                              <1> 
  3805 0000BD4E 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3806 0000BD55 760D                <1> 	jna	short csftdf2_read_sf_clust_2
  3807                              <1> 
  3808 0000BD57 53                  <1> 	push	ebx ; *	
  3809                              <1> 
  3810                              <1> csftdf2_read_sf_clust_next:
  3811 0000BD58 E836FFFFFF          <1> 	call	csftdf2_print_percentage
  3812                              <1> 
  3813                              <1> csftdf2_read_sf_clust_0:
  3814 0000BD5D 8B35[806A0100]      <1> 	mov	esi, [csftdf_sf_drv_dt]	
  3815                              <1> csftdf2_read_sf_clust_1:
  3816 0000BD63 5B                  <1> 	pop	ebx ; *
  3817                              <1> 
  3818                              <1> csftdf2_read_sf_clust_2:
  3819 0000BD64 89DA                <1> 	mov	edx, ebx
  3820 0000BD66 0315[6C6A0100]      <1> 	add	edx, [csftdf_r_size]
  3821 0000BD6C 81FA00000800        <1> 	cmp	edx, Cluster_Buffer + 65536
  3822 0000BD72 772F                <1> 	ja	short csftdf2_write_df_cluster
  3823                              <1> 
  3824 0000BD74 E858FFFFFF          <1> 	call	csftdf2_read_file_sectors ; 19/03/2016
  3825 0000BD79 0F8280020000        <1>         jc      csftdf2_save_fat_file_err2 ; eocc! or disk error! 
  3826                              <1> 
  3827 0000BD7F 09D2                <1> 	or	edx, edx ; edx > 0 -> EOF
  3828 0000BD81 7520                <1> 	jnz	short csftdf2_write_df_cluster
  3829                              <1> 
  3830 0000BD83 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3831 0000BD8A 76D8                <1> 	jna	short csftdf2_read_sf_clust_2
  3832                              <1> 
  3833 0000BD8C 53                  <1> 	push	ebx ; *	
  3834                              <1> 
  3835                              <1> 	; Set cursor position
  3836                              <1> 	; AH= 02h, BH= Page Number, DH= Row, DL= Column
  3837 0000BD8D 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  3838 0000BD93 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  3839 0000BD9A B402                <1> 	mov	ah, 2
  3840 0000BD9C E83D59FFFF          <1> 	call	_int10h
  3841 0000BDA1 EBB5                <1> 	jmp	short csftdf2_read_sf_clust_next
  3842                              <1> 
  3843                              <1> csftdf2_write_df_cluster:
  3844                              <1> 	; 19/03/2016
  3845 0000BDA3 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt]	
  3846 0000BDA9 BB00000700          <1> 	mov	ebx, Cluster_Buffer ; buffer address (64KB)
  3847                              <1> 
  3848                              <1> csftdf2_write_df_clust_next:
  3849 0000BDAE E855000000          <1> 	call	csftdf2_write_file_sectors ; 19/03/2016
  3850 0000BDB3 0F8246020000        <1>         jc      csftdf2_save_fat_file_err2 ; eocc! or disk error! 
  3851                              <1> 
  3852 0000BDB9 09D2                <1> 	or	edx, edx ; edx > 0 -> EOF
  3853 0000BDBB 750A                <1> 	jnz	short csftdf2_rw_f_clust_ok
  3854                              <1> 
  3855 0000BDBD 81FB00000800        <1> 	cmp	ebx, Cluster_Buffer + 65536
  3856 0000BDC3 72E9                <1> 	jb	short csftdf2_write_df_clust_next
  3857                              <1> 	
  3858 0000BDC5 EB82                <1> 	jmp	short csftdf2_read_sf_cluster
  3859                              <1>  
  3860                              <1> csftdf2_rw_f_clust_ok:
  3861 0000BDC7 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3862 0000BDCE 0F86B2010000        <1>         jna     csftdf2_save_fat_file_4 ; 25/03/2016
  3863                              <1> 
  3864                              <1> 	; "100%"
  3865 0000BDD4 BF[2F190100]        <1> 	mov	edi, percentagestr
  3866 0000BDD9 B031                <1> 	mov	al, '1'
  3867 0000BDDB AA                  <1> 	stosb
  3868 0000BDDC B030                <1> 	mov	al, '0'
  3869 0000BDDE AA                  <1> 	stosb
  3870 0000BDDF AA                  <1> 	stosb
  3871                              <1> 
  3872 0000BDE0 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  3873 0000BDE6 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  3874 0000BDED B402                <1> 	mov	ah, 2
  3875 0000BDEF E8EA58FFFF          <1> 	call	_int10h
  3876                              <1> 
  3877 0000BDF4 BE[2F190100]        <1> 	mov	esi, percentagestr
  3878 0000BDF9 E807AEFFFF          <1> 	call	print_msg
  3879                              <1> 
  3880 0000BDFE E983010000          <1>         jmp     csftdf2_save_fat_file_4
  3881                              <1> 
  3882                              <1> csftdf2_load_fs_file:
  3883                              <1> 	; temporary - 18/03/2016
  3884 0000BE03 E96F020000          <1>         jmp     csftdf2_read_error
  3885                              <1> 
  3886                              <1> csftdf2_write_file_sectors:
  3887                              <1> 	; 19/03/2016
  3888 0000BE08 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  3889 0000BE0C 0F86F1050000        <1>         jna     csftdf2_write_fs_file_sectors
  3890                              <1> 
  3891                              <1> csftdf2_write_fat_file_sectors:
  3892                              <1> 	; 19/03/2016
  3893                              <1> 	; 18/03/2016
  3894                              <1> 	; return:
  3895                              <1> 	;   CF = 0 & EDX > 0 -> END OF FILE
  3896                              <1> 	;   CF = 0 & EDX = 0 -> not EOF
  3897                              <1> 	;   CF = 1 -> write error (error code in AL)	
  3898                              <1> 
  3899                              <1> csftdf2_write_fat_file_secs_0:
  3900 0000BE12 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  3901 0000BE18 2B15[786A0100]      <1> 	sub	edx, [csftdf_df_wbytes]
  3902 0000BE1E 3B15[706A0100]      <1> 	cmp	edx, [csftdf_w_size]	
  3903 0000BE24 7306                <1> 	jnb	short csftdf2_write_fat_file_secs_1
  3904 0000BE26 8915[706A0100]      <1> 	mov	[csftdf_w_size], edx		
  3905                              <1> 
  3906                              <1> csftdf2_write_fat_file_secs_1:
  3907 0000BE2C A1[706A0100]        <1> 	mov	eax, [csftdf_w_size]
  3908 0000BE31 29D2                <1> 	sub	edx, edx
  3909 0000BE33 0FB74E11            <1> 	movzx	ecx, word [esi+LD_BPB+BytesPerSec]
  3910 0000BE37 01C8                <1> 	add	eax, ecx
  3911 0000BE39 48                  <1> 	dec	eax
  3912 0000BE3A F7F1                <1> 	div	ecx
  3913 0000BE3C 89C1                <1> 	mov	ecx, eax ; sector count
  3914 0000BE3E A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster]
  3915                              <1> 
  3916                              <1> 	; EBX = memory block address (current)	
  3917                              <1> 
  3918 0000BE43 E8A20F0000          <1> 	call	write_fat_file_sectors
  3919 0000BE48 7259                <1> 	jc	short csftdf2_write_fat_file_secs_4
  3920                              <1> 
  3921                              <1> 	; EBX = next memory address
  3922                              <1> 
  3923 0000BE4A A1[786A0100]        <1> 	mov	eax, [csftdf_df_wbytes]
  3924 0000BE4F 0305[706A0100]      <1> 	add	eax, [csftdf_w_size]
  3925 0000BE55 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  3926 0000BE5B 39D0                <1> 	cmp	eax, edx
  3927 0000BE5D 7344                <1> 	jnb	short csftdf2_write_fat_file_secs_4
  3928 0000BE5F A3[786A0100]        <1> 	mov	[csftdf_df_wbytes], eax
  3929                              <1> 	;
  3930 0000BE64 A3[1A6A0100]        <1> 	mov	[DestinationFile_DirEntry+DirEntry_FileSize], eax
  3931                              <1> 
  3932 0000BE69 53                  <1> 	push	ebx ; *
  3933                              <1> 
  3934 0000BE6A 803D[566A0100]01    <1> 	cmp	byte [DestinationFileFound], 1
  3935 0000BE71 7210                <1> 	jb	short csftdf2_write_fat_file_secs_2
  3936                              <1> 
  3937                              <1> 	; get next cluster (csftdf_w_size! bytes)
  3938 0000BE73 A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster]
  3939 0000BE78 E887050000          <1> 	call	get_next_cluster
  3940 0000BE7D 731C                <1> 	jnc	short csftdf2_write_fat_file_secs_3
  3941                              <1> 
  3942 0000BE7F 21C0                <1> 	and	eax, eax ; end of cluster chain!?
  3943 0000BE81 7521                <1> 	jnz	short csftdf2_write_fat_file_secs_5 ; disk error !
  3944                              <1> 
  3945                              <1> csftdf2_write_fat_file_secs_2:
  3946 0000BE83 A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster] ; last cluster
  3947 0000BE88 E8800E0000          <1> 	call	add_new_cluster		
  3948 0000BE8D 7215                <1> 	jc	short csftdf2_write_fat_file_secs_5
  3949                              <1> 
  3950                              <1> 	; NOTE: Destination file size may be bigger than
  3951                              <1> 	; source file size when the last reading fails after here.
  3952                              <1> 	; (The last -empty- cluster of destination file must be 
  3953                              <1> 	; truncated and LMDT must be current date&time for partial
  3954                              <1> 	; copy result!) 
  3955 0000BE8F 8B15[706A0100]      <1> 	mov	edx, [csftdf_w_size] ; bytes per cluster
  3956 0000BE95 0115[1A6A0100]      <1> 	add	[DestinationFile_DirEntry+DirEntry_FileSize], edx
  3957                              <1> 
  3958                              <1> csftdf2_write_fat_file_secs_3:
  3959 0000BE9B 5B                  <1> 	pop	ebx ; *
  3960 0000BE9C 29D2                <1> 	sub	edx, edx ; 0
  3961 0000BE9E A3[686A0100]        <1> 	mov	[csftdf_df_cluster], eax ; next cluster
  3962                              <1> 
  3963                              <1> csftdf2_write_fat_file_secs_4:
  3964 0000BEA3 C3                  <1> 	retn
  3965                              <1> 
  3966                              <1> csftdf2_write_fat_file_secs_5:
  3967 0000BEA4 5B                  <1> 	pop	ebx ; *
  3968                              <1> 	; 16/10/2016 (1Dh -> 18)
  3969 0000BEA5 B812000000          <1> 	mov	eax, 18 ; Write error !
  3970 0000BEAA C3                  <1> 	retn
  3971                              <1> 
  3972                              <1> csftdf2_save_file:
  3973                              <1> 	; 09/12/2017
  3974                              <1> 	; 25/03/2016
  3975                              <1> 	; 19/03/2016
  3976                              <1> 	; 18/03/2016
  3977 0000BEAB 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt] ; logical dos drv desc. tbl.
  3978                              <1> 
  3979 0000BEB1 8B1D[5C6A0100]      <1> 	mov	ebx, [csftdf_sf_mem_addr] ; memory block address
  3980                              <1> 
  3981 0000BEB7 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  3982 0000BEBB 0F86F4010000        <1>         jna     csftdf2_save_fs_file
  3983                              <1> 
  3984                              <1> csftdf2_save_fat_file:
  3985 0000BEC1 53                  <1> 	push	ebx; *
  3986                              <1> 
  3987 0000BEC2 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  3988 0000BEC9 7724                <1> 	ja	short csftdf2_save_fat_file_0
  3989                              <1> 
  3990                              <1> 	; Set cursor position
  3991                              <1> 	; AH= 02h, BH= Page Number, DH= Row, DL= Column
  3992 0000BECB 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  3993 0000BED1 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  3994 0000BED8 B402                <1> 	mov	ah, 2
  3995 0000BEDA E8FF57FFFF          <1> 	call	_int10h
  3996                              <1> 	
  3997 0000BEDF BE[23190100]        <1> 	mov	esi, msg_writing
  3998 0000BEE4 E81CADFFFF          <1> 	call	print_msg
  3999                              <1> 
  4000                              <1> csftdf2_save_fat_file_next:
  4001 0000BEE9 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt] ; 25/03/2016
  4002                              <1> 
  4003                              <1> csftdf2_save_fat_file_0:
  4004 0000BEEF 5B                  <1> 	pop	ebx ; *
  4005                              <1> 
  4006                              <1> csftdf2_save_fat_file_1:
  4007 0000BEF0 E813FFFFFF          <1> 	call	csftdf2_write_file_sectors ; 19/03/2016	
  4008 0000BEF5 0F827E010000        <1>         jc      csftdf2_rw_error ; eocc! or disk error! 
  4009                              <1> 
  4010 0000BEFB 09D2                <1> 	or	edx, edx ; edx > 0 -> EOF
  4011 0000BEFD 756D                <1>         jnz     short csftdf2_save_fat_file_3 ; 25/03/2016
  4012                              <1> 
  4013 0000BEFF 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  4014 0000BF06 76E8                <1> 	jna	short csftdf2_save_fat_file_1
  4015                              <1> 
  4016 0000BF08 B020                <1> 	mov	al, 20h
  4017 0000BF0A BF[2F190100]        <1> 	mov	edi, percentagestr
  4018 0000BF0F AA                  <1> 	stosb
  4019 0000BF10 AA                  <1> 	stosb
  4020 0000BF11 A1[786A0100]        <1> 	mov	eax, [csftdf_df_wbytes]
  4021 0000BF16 BA64000000          <1> 	mov	edx, 100
  4022 0000BF1B F7E2                <1> 	mul	edx
  4023 0000BF1D 8B0D[586A0100]      <1> 	mov	ecx, [csftdf_filesize]	
  4024 0000BF23 F7F1                <1> 	div	ecx
  4025 0000BF25 B10A                <1> 	mov	cl, 10
  4026 0000BF27 F6F1                <1> 	div	cl
  4027 0000BF29 80C430              <1> 	add	ah, '0'
  4028 0000BF2C 8827                <1> 	mov	[edi], ah
  4029 0000BF2E 20C0                <1> 	and	al, al
  4030 0000BF30 740A                <1> 	jz	short csftdf2_save_fat_file_2
  4031 0000BF32 4F                  <1> 	dec	edi
  4032                              <1> 	;cbw
  4033 0000BF33 30E4                <1> 	xor	ah, ah ; 09/12/2017
  4034 0000BF35 F6F1                <1> 	div	cl
  4035 0000BF37 80C430              <1> 	add	ah, '0'
  4036 0000BF3A 8827                <1> 	mov	[edi], ah
  4037                              <1> 	;and	al, al
  4038                              <1> 	;jz	short csftdf2_save_fat_file_2
  4039                              <1> 	;dec	edi
  4040                              <1> 	;mov	[edi], '1' ; 100%		
  4041                              <1> 
  4042                              <1> csftdf2_save_fat_file_2:
  4043 0000BF3C 53                  <1> 	push	ebx ; *
  4044                              <1> 
  4045 0000BF3D E802000000          <1> 	call	csftdf2_print_wr_percentage ; 25/03/2016
  4046                              <1> 
  4047 0000BF42 EBA5                <1>         jmp     csftdf2_save_fat_file_next
  4048                              <1> 
  4049                              <1> csftdf2_print_wr_percentage:
  4050                              <1> 	; Set cursor position
  4051                              <1> 	; AH= 02h, BH= Page Number, DH= Row, DL= Column
  4052 0000BF44 8A3D[7D6A0100]      <1> 	mov	bh, [csftdf_videopage]
  4053 0000BF4A 668B15[7E6A0100]    <1> 	mov	dx, [csftdf_cursorpos]
  4054 0000BF51 B402                <1> 	mov	ah, 2
  4055 0000BF53 E88657FFFF          <1> 	call	_int10h
  4056                              <1> 
  4057 0000BF58 BE[23190100]        <1> 	mov	esi, msg_writing
  4058 0000BF5D E8A3ACFFFF          <1> 	call	print_msg
  4059                              <1> 
  4060 0000BF62 BE[2F190100]        <1> 	mov	esi, percentagestr
  4061                              <1> 	;call	print_msg
  4062                              <1> 	;retn
  4063 0000BF67 E999ACFFFF          <1> 	jmp	print_msg
  4064                              <1> 
  4065                              <1> csftdf2_save_fat_file_3:
  4066 0000BF6C 803D[7C6A0100]00    <1> 	cmp	byte [csftdf_percentage], 0
  4067 0000BF73 7611                <1>         jna     csftdf2_save_fat_file_4 ; 25/03/2016
  4068                              <1> 
  4069                              <1> 	; "100%"
  4070 0000BF75 BF[2F190100]        <1> 	mov	edi, percentagestr
  4071 0000BF7A B031                <1> 	mov	al, '1'
  4072 0000BF7C AA                  <1> 	stosb
  4073 0000BF7D B030                <1> 	mov	al, '0'
  4074 0000BF7F AA                  <1> 	stosb
  4075 0000BF80 AA                  <1> 	stosb
  4076                              <1> 
  4077 0000BF81 E8BEFFFFFF          <1> 	call	csftdf2_print_wr_percentage
  4078                              <1> 
  4079                              <1> csftdf2_save_fat_file_4:
  4080 0000BF86 803D[566A0100]00    <1> 	cmp	byte [DestinationFileFound], 0
  4081 0000BF8D 7647                <1> 	jna	short csftdf2_save_fat_file_6
  4082                              <1> 
  4083 0000BF8F 8B35[846A0100]      <1> 	mov	esi, [csftdf_df_drv_dt] ; 31/03/2016	
  4084                              <1> 
  4085 0000BF95 A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster] ; last cluster
  4086 0000BF9A E865040000          <1> 	call	get_next_cluster
  4087 0000BF9F 7235                <1> 	jc	short csftdf2_save_fat_file_6 ; eocc! or disk error!
  4088                              <1> 
  4089 0000BFA1 A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster] ; last cluster
  4090                              <1> 	;xor	ecx, ecx
  4091                              <1> 	;mov	[FAT_ClusterCounter], ecx ; 0 ; reset
  4092                              <1> 	;dec	ecx ; 0FFFFFFFFh
  4093                              <1> 	;shr	ecx, 4 ; 28 bit ; 0FFFFFFFh
  4094 0000BFA6 B9FFFFFF0F          <1> 	mov	ecx, 0FFFFFFFh
  4095 0000BFAB E87E070000          <1> 	call	update_cluster
  4096 0000BFB0 7224                <1> 	jc	short csftdf2_save_fat_file_6 ; really last cluster!?
  4097                              <1> 
  4098 0000BFB2 A3[686A0100]        <1> 	mov	[csftdf_df_cluster], eax ; next cluster
  4099                              <1> 	
  4100                              <1> 	; byte [FAT_BuffValidData] = 2 
  4101 0000BFB7 E82F0A0000          <1> 	call	save_fat_buffer
  4102 0000BFBC 730E                <1> 	jnc	short csftdf2_save_fat_file_5
  4103                              <1> 	
  4104 0000BFBE 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  4105 0000BFC4 8915[1A6A0100]      <1> 	mov	[DestinationFile_DirEntry+DirEntry_FileSize], edx
  4106 0000BFCA EB58                <1> 	jmp	short csftdf2_save_fat_file_err3
  4107                              <1> 
  4108                              <1> csftdf2_save_fat_file_5:
  4109 0000BFCC A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster]
  4110                              <1> 
  4111                              <1> 	; EAX = First cluster to be truncated/unlinked
  4112                              <1> 	; ESI = Logical dos drive description table address
  4113 0000BFD1 E8580C0000          <1> 	call	truncate_cluster_chain
  4114                              <1> 
  4115                              <1> csftdf2_save_fat_file_6:
  4116                              <1> 	; 28/03/2016
  4117 0000BFD6 BE[89690100]        <1> 	mov	esi, SourceFile_DirEntry+DirEntry_Attr ; +11 to + 18
  4118 0000BFDB BF[096A0100]        <1> 	mov	edi, DestinationFile_DirEntry+DirEntry_Attr ; +11 to + 18
  4119 0000BFE0 A4                  <1> 	movsb ; +11
  4120 0000BFE1 A5                  <1> 	movsd ; +12 .. +15
  4121 0000BFE2 66A5                <1> 	movsw ; +16 .. +17
  4122                              <1> 		; + 18
  4123 0000BFE4 83C604              <1> 	add	esi, 4
  4124 0000BFE7 83C704              <1> 	add	edi, 4
  4125 0000BFEA A5                  <1> 	movsd	; DirEntry_WrtTime ; +22 .. +25
  4126                              <1> 
  4127 0000BFEB 8B15[586A0100]      <1> 	mov	edx, [csftdf_filesize]
  4128 0000BFF1 8915[1A6A0100]      <1> 	mov	[DestinationFile_DirEntry+DirEntry_FileSize], edx
  4129                              <1> 
  4130 0000BFF7 E8BAF0FFFF          <1> 	call	convert_current_date_time
  4131                              <1> 	; DX = Date in dos dir entry format
  4132                              <1> 	; AX = Time in dos dir entry format
  4133 0000BFFC EB4D                <1> 	jmp	short csftdf2_save_fat_file_7
  4134                              <1> 
  4135                              <1> csftdf2_save_fat_file_err1:
  4136 0000BFFE 5B                  <1> 	pop	ebx ; *	
  4137                              <1> csftdf2_save_fat_file_err2:
  4138 0000BFFF A1[786A0100]        <1> 	mov	eax, [csftdf_df_wbytes]
  4139 0000C004 8B15[1A6A0100]      <1> 	mov	edx, [DestinationFile_DirEntry+DirEntry_FileSize]
  4140 0000C00A 39C2                <1> 	cmp	edx, eax
  4141 0000C00C 7616                <1> 	jna	short csftdf2_save_fat_file_err3
  4142 0000C00E A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster] ; last (empty) cluster
  4143                              <1> 	; ESI = Logical dos drive description table address
  4144 0000C013 E8160C0000          <1> 	call	truncate_cluster_chain
  4145 0000C018 720A                <1> 	jc	short csftdf2_save_fat_file_err3
  4146 0000C01A A1[786A0100]        <1> 	mov	eax, [csftdf_df_wbytes]	
  4147 0000C01F A3[1A6A0100]        <1> 	mov	[DestinationFile_DirEntry+DirEntry_FileSize], eax
  4148                              <1> csftdf2_save_fat_file_err3:
  4149 0000C024 E88DF0FFFF          <1> 	call	convert_current_date_time
  4150                              <1> 	; DX = Date in dos dir entry format
  4151                              <1> 	; AX = Time in dos dir entry format
  4152 0000C029 C605[0B6A0100]00    <1> 	mov	byte [DestinationFile_DirEntry+DirEntry_CrtTimeTenth], 0
  4153 0000C030 66A3[0C6A0100]      <1> 	mov	[DestinationFile_DirEntry+DirEntry_CrtTime], ax
  4154 0000C036 668915[0E6A0100]    <1> 	mov	[DestinationFile_DirEntry+DirEntry_CrtDate], dx		
  4155 0000C03D 66A3[146A0100]      <1> 	mov	[DestinationFile_DirEntry+DirEntry_WrtTime], ax
  4156 0000C043 668915[166A0100]    <1> 	mov	[DestinationFile_DirEntry+DirEntry_WrtDate], dx
  4157 0000C04A F9                  <1> 	stc
  4158                              <1> csftdf2_save_fat_file_7:
  4159 0000C04B 9C                  <1> 	pushf
  4160 0000C04C 668915[106A0100]    <1> 	mov	[DestinationFile_DirEntry+DirEntry_LastAccDate], dx
  4161 0000C053 BE[FE690100]        <1> 	mov	esi, DestinationFile_DirEntry
  4162 0000C058 BF00000800          <1> 	mov	edi, Directory_Buffer
  4163 0000C05D 0FB70D[266A0100]    <1> 	movzx	ecx, word [DestinationFile_DirEntryNumber] ; (<2048)
  4164 0000C064 66C1E105            <1> 	shl	cx, 5 ; 32 * directory entry number
  4165 0000C068 01CF                <1> 	add	edi, ecx
  4166                              <1> 	;mov	ecx, 8
  4167 0000C06A 66B90800            <1> 	mov	cx, 8
  4168 0000C06E F3A5                <1> 	rep	movsd
  4169 0000C070 9D                  <1> 	popf
  4170 0000C071 730B                <1> 	jnc	short csftdf2_write_file_OK
  4171                              <1> 	 		
  4172                              <1> csftdf2_write_error:
  4173                              <1> 	; 18/03/2016
  4174 0000C073 B01D                <1> 	mov	al, 1Dh ; write error
  4175 0000C075 EB02                <1> 	jmp	short csftdf2_rw_error
  4176                              <1> 
  4177                              <1> 	; 16/03/2016
  4178                              <1> csftdf2_read_error:
  4179 0000C077 B011                <1> 	mov	al, 17 ; ; Drive not ready or read error!
  4180                              <1> csftdf2_rw_error:
  4181 0000C079 A2[556A0100]        <1> 	mov	[csftdf_rw_err], al 
  4182                              <1> 
  4183                              <1> csftdf2_write_file_OK:
  4184                              <1> 	; 18/03/2016
  4185 0000C07E C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  4186 0000C085 E8CAF0FFFF          <1> 	call	save_directory_buffer
  4187                              <1> 
  4188                              <1>  	; Update last modification date&time of destination
  4189                              <1> 	; file's (parent) directory
  4190 0000C08A E860F1FFFF          <1> 	call	update_parent_dir_lmdt
  4191                              <1> 	;
  4192 0000C08F A1[5C6A0100]        <1> 	mov	eax, [csftdf_sf_mem_addr] ; start address
  4193                              <1> 
  4194 0000C094 21C0                <1> 	and	eax, eax
  4195 0000C096 750E                <1> 	jnz	short csftdf2_dealloc_mblock
  4196                              <1> 
  4197 0000C098 88C5                <1> 	mov	ch, al ; 0 (Cluster r/w, not full loading)
  4198                              <1> csftdf2_dealloc_retn:
  4199 0000C09A 8A0D[556A0100]      <1> 	mov	cl, [csftdf_rw_err]
  4200 0000C0A0 A1[686A0100]        <1> 	mov	eax, [csftdf_df_cluster]
  4201 0000C0A5 C3                  <1> 	retn
  4202                              <1> 
  4203                              <1> csftdf2_dealloc_mblock:
  4204 0000C0A6 8B0D[606A0100]      <1> 	mov	ecx, [csftdf_sf_mem_bsize] ; block size	
  4205 0000C0AC E8EB9CFFFF          <1> 	call	deallocate_memory_block
  4206 0000C0B1 B5FF                <1>         mov     ch, 0FFh ; (File was full loaded at memory)
  4207 0000C0B3 EBE5                <1> 	jmp	short csftdf2_dealloc_retn
  4208                              <1> 
  4209                              <1> csftdf2_save_fs_file:
  4210                              <1> 	; 16/10/2016 (1Dh -> 18)
  4211                              <1> 	; temporary - (21/03/2016)
  4212 0000C0B5 B812000000          <1> 	mov	eax, 18 ; write error
  4213 0000C0BA F9                  <1> 	stc
  4214 0000C0BB C3                  <1> 	retn
  4215                              <1> 
  4216                              <1> create_file:
  4217                              <1> 	; 16/10/2016
  4218                              <1> 	; 24/03/2016, 31/03/2016
  4219                              <1> 	; 20/03/2016, 21/03/2016, 23/03/2016
  4220                              <1> 	; 19/03/2016 (TRDOS 396 = TRDOS v2.0)
  4221                              <1> 	; 03/09/2011 (FILE.ASM, 'proc_create_file')
  4222                              <1> 	; 09/08/2010
  4223                              <1> 	;
  4224                              <1> 	; INPUT ->
  4225                              <1> 	; 	EAX = File Size
  4226                              <1> 	; 	ESI = ASCIIZ File Name
  4227                              <1> 	; 	CL = File Attributes 
  4228                              <1> 	;	EBX = FFFFFFFFh -> create empty file 
  4229                              <1> 	;			 (only for FAT fs) 
  4230                              <1> 	; OUTPUT ->
  4231                              <1> 	;     CF = 0 ->
  4232                              <1> 	;	EAX = New file's first cluster
  4233                              <1> 	; 	ESI = Logical Dos Drv Descr. Table Addr.
  4234                              <1> 	; 	EBX = offset CreateFile_Size
  4235                              <1> 	; 	ECX = Sectors per cluster (<256) 
  4236                              <1> 	; 	EDX = Directory entry index/number (<65536)
  4237                              <1> 	;     CF = 1 -> error code in AL
  4238                              <1> 
  4239                              <1> ;	test	cl, 18h (directory or volume name)
  4240                              <1> ;	jnz	short loc_createfile_access_denied
  4241 0000C0BC 80E107              <1> 	and	cl, 07h ; S, H, R
  4242 0000C0BF 880D[A46A0100]      <1>         mov     [createfile_attrib], cl 
  4243                              <1> 
  4244 0000C0C5 89D9                <1> 	mov	ecx, ebx
  4245 0000C0C7 89F3                <1> 	mov	ebx, esi ; ASCIIZ File Name address
  4246 0000C0C9 29D2                <1> 	sub	edx, edx
  4247 0000C0CB 8A35[465F0100]      <1>         mov     dh, [Current_Drv]
  4248 0000C0D1 BE00010900          <1>         mov     esi, Logical_DOSDisks
  4249 0000C0D6 01D6                <1> 	add	esi, edx
  4250                              <1> 
  4251 0000C0D8 8815[AF6A0100]      <1> 	mov	[createfile_UpdatePDir], dl ; 0 ; 31/03/2016 
  4252                              <1> 
  4253                              <1> 	; LD_DiskType = 0 for write protection (read only) 
  4254 0000C0DE 807E0101            <1> 	cmp	byte [esi+LD_DiskType], 1 ; 0 = Invalid
  4255 0000C0E2 730A                <1> 	jnb	short loc_createfile_check_file_sytem
  4256                              <1> 	; 16/10/2016 (TRDOS Error code: 30, disk write protected) 
  4257 0000C0E4 B81E000000          <1> 	mov	eax, 30 ; 13h, MSDOS err : Disk write-protected 
  4258 0000C0E9 66BA0000            <1> 	mov	dx, 0
  4259                              <1> 	; err retn: EDX = 0, EBX = File name offset
  4260                              <1> 	; ESI -> Dos drive description table address	
  4261 0000C0ED C3                  <1> 	retn
  4262                              <1> 
  4263                              <1> ;loc_createfile_access_denied:
  4264                              <1> ;	mov	eax, 05h ; access denied (invalid attributes input)
  4265                              <1> ;	stc
  4266                              <1> ;	retn
  4267                              <1> 
  4268                              <1> loc_createfile_check_file_sytem:
  4269 0000C0EE 807E0301            <1> 	cmp	byte [esi+LD_FATType], 1
  4270 0000C0F2 730A                <1> 	jnb	short loc_createfile_chk_empty_FAT_file_sign1
  4271                              <1> 
  4272 0000C0F4 A3[906A0100]        <1> 	mov	[createfile_size], eax
  4273                              <1> 	; ESI = Logical Dos Drive Description Table address
  4274                              <1> 	; EBX = ASCIIZ File Name address
  4275 0000C0F9 E9FE020000          <1> 	jmp	create_fs_file
  4276                              <1> 
  4277                              <1> loc_createfile_chk_empty_FAT_file_sign1:
  4278                              <1> 	; ECX = FFFFFFFFh -> create empty file if drive has FAT fs
  4279 0000C0FE 41                  <1> 	inc	ecx
  4280 0000C0FF 7506                <1> 	jnz	short loc_createfile_chk_empty_FAT_file_sign2
  4281 0000C101 890D[906A0100]      <1> 	mov	[createfile_size], ecx ; 0 ; empty file
  4282                              <1> 
  4283                              <1> loc_createfile_chk_empty_FAT_file_sign2:
  4284                              <1> 	; 23/03/2016
  4285 0000C107 668B4E11            <1> 	mov	cx, [esi+LD_BPB+BytesPerSec]
  4286 0000C10B 66890D[AC6A0100]    <1> 	mov	[createfile_BytesPerSec], cx
  4287                              <1> 	
  4288                              <1> 	; EBX = ASCIIZ File Name address
  4289 0000C112 0FB65613            <1> 	movzx	edx, byte [esi+LD_BPB+SecPerClust]
  4290 0000C116 8815[A56A0100]      <1> 	mov	[createfile_SecPerClust], dl
  4291 0000C11C 8B4E74              <1> 	mov	ecx, [esi+LD_FreeSectors]
  4292 0000C11F 39D1                <1> 	cmp	ecx, edx ; byte [createfile_SecPerClust]
  4293 0000C121 7306                <1> 	jnb	short loc_create_fat_file
  4294                              <1> 	  
  4295                              <1> loc_createfile_insufficient_disk_space:
  4296 0000C123 B827000000          <1> 	mov	eax, 27h
  4297                              <1> loc_createfile_gffc_retn:
  4298 0000C128 C3                  <1> 	retn
  4299                              <1> 
  4300                              <1> loc_create_fat_file:
  4301 0000C129 891D[886A0100]      <1> 	mov	[createfile_Name_Offset], ebx
  4302 0000C12F 890D[8C6A0100]      <1> 	mov	[createfile_FreeSectors], ecx
  4303                              <1> 
  4304                              <1> loc_createfile_gffc_1:
  4305 0000C135 E821050000          <1> 	call	get_first_free_cluster
  4306 0000C13A 72EC                <1> 	jc	short loc_createfile_gffc_retn
  4307                              <1> 
  4308 0000C13C A3[946A0100]        <1> 	mov	[createfile_FFCluster], eax
  4309                              <1> 
  4310                              <1> loc_createfile_locate_ffe_on_directory:
  4311                              <1> 	; Current directory fcluster <> Directory buffer cluster
  4312                              <1> 	; Current directory will be reloaded by
  4313                              <1> 	; 'locate_current_dir_file' procedure
  4314                              <1> 	;
  4315                              <1> 	; ESI = Logical Dos Drv Desc. Table Adress
  4316 0000C141 56                  <1> 	push	esi ; *
  4317 0000C142 31C0                <1> 	xor	eax, eax
  4318                              <1> 
  4319 0000C144 A3[62660100]        <1> 	mov	dword [FAT_ClusterCounter], eax ; 0
  4320                              <1> 	; 21/03/2016
  4321 0000C149 A2[AE6A0100]        <1> 	mov	byte [createfile_wfc], al ; 0 
  4322                              <1> 
  4323 0000C14E 89C1                <1>  	mov	ecx, eax
  4324 0000C150 6649                <1> 	dec	cx ; FFFFh  
  4325                              <1> 	; CX = FFFFh -> find first deleted or free entry
  4326                              <1> 	; ESI would be ASCIIZ filename address if the call
  4327                              <1> 	; would not be for first free or deleted dir entry  
  4328 0000C152 E8D7E7FFFF          <1> 	call	locate_current_dir_file
  4329 0000C157 0F83EE000000        <1> 	jnc	loc_createfile_set_ff_dir_entry
  4330 0000C15D 5E                  <1> 	pop	esi ; *
  4331                              <1> 	 ; ESI = Logical DOS Drv. Description Table Address 
  4332 0000C15E 83F802              <1> 	cmp	eax, 2
  4333 0000C161 7402                <1> 	je	short loc_createfile_add_new_cluster
  4334                              <1> loc_createfile_locate_file_stc_retn:
  4335 0000C163 F9                  <1> 	stc
  4336 0000C164 C3                  <1> 	retn
  4337                              <1> 
  4338                              <1> loc_createfile_add_new_cluster:
  4339 0000C165 803D[455F0100]02    <1> 	cmp	byte [Current_FATType], 2
  4340                              <1> 	;cmp	byte [esi+LD_FATType], 2
  4341 0000C16C 770C                <1> 	ja	short loc_createfile_add_new_cluster_check_fsc
  4342 0000C16E 803D[445F0100]01    <1> 	cmp	byte [Current_Dir_Level], 1
  4343                              <1> 	;cmp	byte [esi+LD_CDirLevel], 1
  4344 0000C175 7303                <1> 	jnb	short loc_createfile_add_new_cluster_check_fsc
  4345                              <1> 	
  4346                              <1> 	;mov	eax, 12
  4347 0000C177 B00C                <1> 	mov	al, 12 ; No more files 
  4348                              <1> 
  4349                              <1> loc_createfile_anc_retn:
  4350 0000C179 C3                  <1> 	retn
  4351                              <1> 
  4352                              <1> loc_createfile_add_new_cluster_check_fsc:
  4353 0000C17A 8B0D[8C6A0100]      <1> 	mov	ecx, [createfile_FreeSectors]
  4354 0000C180 0FB605[A56A0100]    <1> 	movzx	eax, byte [createfile_SecPerClust]
  4355 0000C187 66D1E0              <1> 	shl	ax, 1 ; AX = 2 * AX
  4356 0000C18A 39C1                <1> 	cmp	ecx, eax
  4357 0000C18C 7295                <1>         jb	short loc_createfile_insufficient_disk_space
  4358                              <1> 
  4359                              <1> loc_createfile_add_new_subdir_cluster:
  4360 0000C18E 8B15[71660100]      <1> 	mov	edx, [DirBuff_Cluster]
  4361 0000C194 8915[986A0100]      <1> 	mov	[createfile_LastDirCluster], edx	
  4362                              <1> 
  4363 0000C19A A1[946A0100]        <1> 	mov	eax, [createfile_FFCluster]
  4364 0000C19F E846040000          <1> 	call	load_FAT_sub_directory 
  4365 0000C1A4 72D3                <1> 	jc	short loc_createfile_anc_retn
  4366                              <1> 
  4367                              <1> pass_createfile_add_new_subdir_cluster:
  4368                              <1> 	;movzx	eax, word [esi+LD_BPB+BytesPerSec]
  4369 0000C1A6 0FB705[AC6A0100]    <1> 	movzx	eax, word [createfile_BytesPerSec] ; 23/03/2016
  4370 0000C1AD F7E1                <1> 	mul	ecx ; ecx = directory buffer sector count
  4371 0000C1AF 89C1                <1> 	mov	ecx, eax
  4372 0000C1B1 C1E902              <1> 	shr	ecx, 2 ; dword count
  4373 0000C1B4 29C0                <1> 	sub	eax, eax ; 0
  4374 0000C1B6 F3AB                <1> 	rep	stosd 
  4375                              <1> 	;
  4376 0000C1B8 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 
  4377 0000C1BF E890EFFFFF          <1> 	call	save_directory_buffer
  4378 0000C1C4 72B3                <1> 	jc	short loc_createfile_anc_retn
  4379                              <1> 
  4380                              <1> loc_createfile_save_added_subdir_cluster:
  4381 0000C1C6 A1[986A0100]        <1> 	mov	eax, [createfile_LastDirCluster]
  4382 0000C1CB 8B0D[946A0100]      <1> 	mov	ecx, [createfile_FFCluster]
  4383 0000C1D1 E858050000          <1> 	call	update_cluster
  4384 0000C1D6 7304                <1> 	jnc	short loc_createfile_save_fat_buffer_0
  4385 0000C1D8 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  4386 0000C1DA 751A                <1> 	jnz	short loc_createfile_save_fat_buffer_stc_retn
  4387                              <1> 
  4388                              <1> loc_createfile_save_fat_buffer_0:
  4389 0000C1DC A1[946A0100]        <1> 	mov	eax, [createfile_FFCluster]
  4390 0000C1E1 A3[986A0100]        <1> 	mov	[createfile_LastDirCluster], eax
  4391 0000C1E6 B9FFFFFF0F          <1> 	mov	ecx, 0FFFFFFFh ; 28 bit
  4392 0000C1EB E83E050000          <1> 	call	update_cluster
  4393 0000C1F0 7306                <1> 	jnc	short loc_createfile_save_fat_buffer_1
  4394 0000C1F2 09C0                <1> 	or	eax, eax ; Was it free cluster
  4395 0000C1F4 7402                <1> 	jz	short loc_createfile_save_fat_buffer_1
  4396                              <1> 
  4397                              <1> loc_createfile_save_fat_buffer_stc_retn:
  4398 0000C1F6 F9                  <1> 	stc
  4399                              <1> loc_createfile_save_fat_buffer_retn:
  4400                              <1> loc_createfile_gffc_2_stc_retn:
  4401 0000C1F7 C3                  <1> 	retn
  4402                              <1> 
  4403                              <1> loc_createfile_save_fat_buffer_1:
  4404                              <1> 	; byte [FAT_BuffValidData] = 2 
  4405 0000C1F8 E8EE070000          <1> 	call	save_fat_buffer
  4406 0000C1FD 72F8                <1> 	jc	short loc_createfile_save_fat_buffer_retn
  4407                              <1> 
  4408 0000C1FF 803D[62660100]01    <1> 	cmp	byte [FAT_ClusterCounter], 1
  4409 0000C206 7222                <1> 	jb	short loc_createfile_save_fat_buffer_2
  4410                              <1> 
  4411                              <1> 	; ESI = Logical DOS Drive Description Table address 
  4412 0000C208 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  4413                              <1> 
  4414 0000C20D C605[62660100]00    <1> 	mov	byte [FAT_ClusterCounter], 0 ; 21/03/2016
  4415                              <1> 
  4416 0000C214 66BB01FF            <1> 	mov	bx, 0FF01h ; add free clusters 
  4417 0000C218 E863080000          <1> 	call	calculate_fat_freespace
  4418                              <1> 
  4419                              <1> 	;inc	eax ; 0FFFFFFFFh -> 0 ; recalculation is needed!
  4420                              <1> 	;jnz	short loc_createfile_save_fat_buffer_2
  4421                              <1> 
  4422                              <1> 	; ecx > 0 -> Recalculation is needed
  4423 0000C21D 09C9                <1> 	or	ecx, ecx 
  4424 0000C21F 7409                <1> 	jz	short loc_createfile_save_fat_buffer_2
  4425                              <1> 
  4426 0000C221 66BB00FF            <1> 	mov	bx, 0FF00h ; ; recalculate free space
  4427 0000C225 E856080000          <1> 	call	calculate_fat_freespace
  4428                              <1> 
  4429                              <1> loc_createfile_save_fat_buffer_2:
  4430                              <1> 	;call	update_parent_dir_lmdt
  4431                              <1> 
  4432                              <1> loc_createfile_gffc_2:
  4433 0000C22A E82C040000          <1> 	call	get_first_free_cluster
  4434 0000C22F 72C6                <1> 	jc	short loc_createfile_gffc_2_stc_retn
  4435                              <1> 
  4436 0000C231 A3[946A0100]        <1> 	mov	[createfile_FFCluster], eax
  4437                              <1> 
  4438 0000C236 A1[986A0100]        <1> 	mov	eax, [createfile_LastDirCluster]
  4439                              <1> 	
  4440 0000C23B E8AA030000          <1> 	call	load_FAT_sub_directory 
  4441 0000C240 72B5                <1> 	jc	short loc_createfile_gffc_2_stc_retn
  4442                              <1> 
  4443 0000C242 BF00000800          <1> 	mov	edi, Directory_Buffer
  4444                              <1> 
  4445 0000C247 6629DB              <1> 	sub	bx, bx ; directory entry index/number = 0
  4446                              <1> 
  4447 0000C24A 56                  <1> 	push	esi ; * ; 23/03/2016
  4448                              <1> 
  4449                              <1> loc_createfile_set_ff_dir_entry:
  4450 0000C24B 66891D[A66A0100]    <1> 	mov	[createfile_DirIndex], bx
  4451                              <1> 
  4452                              <1>         ; EDI = Directory entry address
  4453 0000C252 8B35[886A0100]      <1> 	mov	esi, [createfile_Name_Offset]
  4454 0000C258 A1[946A0100]        <1> 	mov	eax, [createfile_FFCluster]
  4455 0000C25D A3[9C6A0100]        <1> 	mov	[createfile_Cluster], eax ; 24/03/2016
  4456 0000C262 B5FF                <1> 	mov	ch, 0FFh
  4457 0000C264 8A0D[A46A0100]      <1>         mov	cl, [createfile_attrib] ; file attributes
  4458                              <1> 	; CH > 0 -> File size is in [EBX]
  4459 0000C26A BB[906A0100]        <1> 	mov	ebx, createfile_size
  4460                              <1>   
  4461 0000C26F E803EEFFFF          <1> 	call	make_directory_entry
  4462                              <1> 	
  4463 0000C274 5E                  <1> 	pop	esi ; * ; ESI = Logical Dos Drv Desc. Table address
  4464                              <1> 
  4465 0000C275 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 
  4466 0000C27C E8D3EEFFFF          <1> 	call	save_directory_buffer
  4467 0000C281 7221                <1> 	jc	short loc_createfile_set_ff_dir_entry_retn
  4468                              <1> 
  4469 0000C283 C605[AF6A0100]01    <1> 	mov	byte [createfile_UpdatePDir], 1 ; 31/03/2016 
  4470                              <1> 
  4471                              <1> loc_createfile_get_set_write_file_cluster:
  4472 0000C28A A1[906A0100]        <1> 	mov	eax, [createfile_size]
  4473 0000C28F 09C0                <1> 	or	eax, eax
  4474 0000C291 7570                <1> 	jnz	short loc_createfile_get_set_wfc_cont
  4475 0000C293 40                  <1> 	inc	eax
  4476                              <1> 	; 23/03/2016
  4477 0000C294 0FB61D[A56A0100]    <1> 	movzx	ebx, byte [createfile_SecPerClust]
  4478                              <1> 	;movzx	ecx, word [esi+LD_BPB+BytesPerSec] ; 512
  4479 0000C29B 0FB70D[AC6A0100]    <1>         movzx   ecx, word [createfile_BytesPerSec] ; 512
  4480 0000C2A2 EB7C                <1> 	jmp	loc_createfile_set_cluster_count 
  4481                              <1> 
  4482                              <1> loc_createfile_set_ff_dir_entry_retn:
  4483 0000C2A4 C3                  <1> 	retn
  4484                              <1> 
  4485                              <1> loc_createfile_write_fcluster_to_disk:
  4486 0000C2A5 034668              <1> 	add	eax, [esi+LD_DATABegin] ; convert to physical address
  4487 0000C2A8 BB00000700          <1> 	mov	ebx, Cluster_Buffer
  4488                              <1> 	; ESI = Logical DOS Drv. Desc. Tbl. address
  4489                              <1> 	; EAX = Disk address
  4490                              <1> 	; EBX = Sector Buffer
  4491                              <1> 	; ECX = sectors per cluster
  4492 0000C2AD E8003B0000          <1> 	call	disk_write
  4493 0000C2B2 7211                <1> 	jc	short loc_createfile_dsk_wr_err
  4494                              <1> 
  4495                              <1> loc_createfile_update_fat_cluster:
  4496                              <1> 	; 21/03/2016	
  4497 0000C2B4 803D[AE6A0100]00    <1> 	cmp	byte [createfile_wfc], 0 
  4498 0000C2BB 7712                <1> 	ja	short loc_createfile_update_fat_cluster_n1
  4499                              <1> 
  4500 0000C2BD FE05[AE6A0100]      <1> 	inc	byte [createfile_wfc] ; 1
  4501 0000C2C3 EB24                <1> 	jmp	short loc_createfile_update_fat_cluster_n2
  4502                              <1> 
  4503                              <1> loc_createfile_dsk_wr_err:
  4504                              <1> 	; 16/10/2016 (1Dh -> 18)
  4505                              <1> 	; 23/03/2016
  4506 0000C2C5 B812000000          <1> 	mov	eax, 18 ; Drive not ready or write error !
  4507 0000C2CA E9BD000000          <1> 	jmp	loc_createfile_stc_retn
  4508                              <1> 
  4509                              <1> loc_createfile_update_fat_cluster_n1:
  4510 0000C2CF A1[A06A0100]        <1> 	mov	eax, [createfile_PCluster]
  4511 0000C2D4 8B0D[9C6A0100]      <1> 	mov	ecx, [createfile_Cluster]
  4512 0000C2DA E84F040000          <1> 	call	update_cluster
  4513 0000C2DF 7308                <1> 	jnc	short loc_createfile_update_fat_cluster_n2
  4514 0000C2E1 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  4515 0000C2E3 0F85A3000000        <1> 	jnz	loc_createfile_stc_retn
  4516                              <1> 
  4517                              <1> loc_createfile_update_fat_cluster_n2:
  4518 0000C2E9 A1[9C6A0100]        <1>         mov	eax, [createfile_Cluster]
  4519 0000C2EE B9FFFFFF0F          <1> 	mov	ecx, 0FFFFFFFh
  4520 0000C2F3 E836040000          <1> 	call	update_cluster
  4521 0000C2F8 734E                <1> 	jnc	short loc_createfile_save_fat_buffer_3
  4522 0000C2FA 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  4523 0000C2FC 744A                <1> 	jz	short loc_createfile_save_fat_buffer_3
  4524                              <1> 
  4525                              <1> loc_createfile_upd_fat_fcluster_stc_retn:
  4526 0000C2FE E989000000          <1> 	jmp	loc_createfile_stc_retn
  4527                              <1> 
  4528                              <1> loc_createfile_get_set_wfc_cont:
  4529                              <1> 	;movzx	ecx, word [esi+LD_BPB+BytesPerSec] ; 512	
  4530 0000C303 0FB70D[AC6A0100]    <1> 	movzx	ecx, word [createfile_BytesPerSec] ; 512
  4531 0000C30A 01C8                <1> 	add	eax, ecx
  4532 0000C30C 48                  <1> 	dec	eax  ; add eax, 511
  4533 0000C30D 29D2                <1> 	sub	edx, edx
  4534 0000C30F F7F1                <1> 	div	ecx
  4535 0000C311 0FB61D[A56A0100]    <1> 	movzx	ebx, byte [createfile_SecPerClust]
  4536 0000C318 01D8                <1> 	add	eax, ebx
  4537 0000C31A 48                  <1> 	dec	eax  ; add eax, SecPerClust - 1
  4538 0000C31B 6631D2              <1> 	xor	dx, dx
  4539 0000C31E F7F3                <1> 	div	ebx
  4540                              <1> 
  4541                              <1> loc_createfile_set_cluster_count:
  4542 0000C320 A3[A86A0100]        <1> 	mov 	[createfile_CCount], eax
  4543                              <1> 	
  4544 0000C325 BF00000700          <1> 	mov	edi, Cluster_Buffer
  4545 0000C32A 89C8                <1> 	mov	eax, ecx ; Bytes per Sector
  4546 0000C32C F7E3                <1> 	mul	ebx ; Sectors per Cluster 
  4547                              <1> 	; EAX = Bytes per Cluster
  4548 0000C32E 89C1                <1> 	mov	ecx, eax
  4549 0000C330 C1E902              <1> 	shr	ecx, 2 ; dword count
  4550 0000C333 31C0                <1> 	xor	eax, eax
  4551 0000C335 F3AB                <1> 	rep	stosd ; clear cluster buffer
  4552                              <1> 
  4553 0000C337 A1[9C6A0100]        <1> 	mov	eax, [createfile_Cluster] ; 24/03/2016
  4554                              <1> 
  4555 0000C33C 89D9                <1> 	mov	ecx, ebx
  4556                              <1> 
  4557                              <1> loc_createfile_get_set_wf_fclust_cont:
  4558 0000C33E 83E802              <1> 	sub	eax, 2
  4559 0000C341 F7E1                <1> 	mul	ecx
  4560                              <1> 	; EAX = Logical DOS disk address (offset)
  4561 0000C343 E95DFFFFFF          <1>         jmp     loc_createfile_write_fcluster_to_disk
  4562                              <1> 
  4563                              <1> loc_createfile_save_fat_buffer_3:
  4564                              <1> 	; byte [FAT_BuffValidData] = 2
  4565 0000C348 E89E060000          <1> 	call	save_fat_buffer
  4566 0000C34D 723D                <1> 	jc	loc_createfile_stc_retn
  4567                              <1> 
  4568                              <1> 	; 21/03/2016
  4569 0000C34F 803D[62660100]01    <1> 	cmp	byte [FAT_ClusterCounter], 1
  4570 0000C356 721B                <1> 	jb	short loc_createfile_save_fat_buffer_4
  4571                              <1> 
  4572                              <1> 	; ESI = Logical DOS Drive Description Table address 
  4573 0000C358 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  4574 0000C35D 66BB01FF            <1> 	mov	bx, 0FF01h ; add free clusters 
  4575 0000C361 E81A070000          <1> 	call	calculate_fat_freespace
  4576                              <1> 
  4577                              <1> 	;inc	eax ; 0FFFFFFFFh -> 0 ; recalculation is needed!
  4578                              <1> 	;jnz	short loc_createfile_save_fat_buffer_4
  4579                              <1> 
  4580                              <1> 	; ecx > 0 -> Recalculation is needed
  4581 0000C366 09C9                <1> 	or	ecx, ecx 
  4582 0000C368 7409                <1> 	jz	short loc_createfile_save_fat_buffer_4
  4583                              <1> 
  4584 0000C36A 66BB00FF            <1> 	mov	bx, 0FF00h ; ; recalculate free space
  4585 0000C36E E80D070000          <1> 	call	calculate_fat_freespace
  4586                              <1> 
  4587                              <1> loc_createfile_save_fat_buffer_4:
  4588 0000C373 FF0D[A86A0100]      <1> 	dec	dword [createfile_CCount]
  4589                              <1> 	;jz	short loc_createfile_upd_dir_modif_date_time
  4590 0000C379 743F                <1> 	jz	short loc_createfile_stc_retn_cc ; 31/03/2016
  4591                              <1> 
  4592                              <1> loc_createfile_get_set_write_next_cluster:
  4593 0000C37B E8DB020000          <1> 	call	get_first_free_cluster
  4594 0000C380 720A                <1> 	jc	short loc_createfile_stc_retn
  4595                              <1> 
  4596                              <1> loc_createfile_get_set_write_next_cluster_1:
  4597 0000C382 83F8FF              <1> 	cmp	eax, 0FFFFFFFFh
  4598 0000C385 7213                <1> 	jb	short loc_createfile_get_set_write_next_cluster_2
  4599                              <1> 
  4600                              <1> loc_createfile_wnc_insufficient_disk_space:	
  4601 0000C387 B827000000          <1> 	mov	eax, 27h ; Insufficient disk space
  4602                              <1> 
  4603                              <1> loc_createfile_stc_retn:
  4604 0000C38C 803D[AE6A0100]01    <1> 	cmp	byte [createfile_wfc], 1
  4605 0000C393 7324                <1> 	jnb	short loc_createfile_err_retn
  4606 0000C395 C3                  <1> 	retn
  4607                              <1> 
  4608                              <1> loc_createfile_wnc_inv_format_retn:
  4609                              <1> 	;mov	eax, 28
  4610 0000C396 B01C                <1> 	mov	al, 28 ; Invalid format
  4611 0000C398 EBF2                <1> 	jmp	short loc_createfile_stc_retn
  4612                              <1> 	         
  4613                              <1> loc_createfile_get_set_write_next_cluster_2:
  4614 0000C39A 83F802              <1> 	cmp	eax, 2
  4615 0000C39D 72F7                <1> 	jb	short loc_createfile_wnc_inv_format_retn
  4616                              <1> 
  4617                              <1> loc_createfile_get_set_write_next_cluster_3:
  4618 0000C39F 8B0D[9C6A0100]      <1> 	mov	ecx, [createfile_Cluster]
  4619 0000C3A5 A3[9C6A0100]        <1> 	mov	[createfile_Cluster], eax
  4620 0000C3AA 890D[A06A0100]      <1> 	mov	[createfile_PCluster], ecx
  4621 0000C3B0 0FB60D[A56A0100]    <1> 	movzx	ecx, byte [createfile_SecPerClust]
  4622 0000C3B7 EB85                <1> 	jmp	short loc_createfile_get_set_wf_fclust_cont
  4623                              <1> 
  4624                              <1> loc_createfile_err_retn:
  4625 0000C3B9 F9                  <1> 	stc
  4626                              <1> 
  4627                              <1> ;loc_createfile_upd_dir_modif_date_time:
  4628                              <1> loc_createfile_stc_retn_cc: ; 31/03/2016
  4629 0000C3BA 9C                  <1> 	pushf	; cpu is here for an error return or completion 
  4630 0000C3BB 50                  <1> 	push	eax ; error code if cf = 1
  4631                              <1> 
  4632                              <1> 	;call	update_parent_dir_lmdt
  4633                              <1> 
  4634                              <1> ;loc_createfile_stc_retn_cc:
  4635 0000C3BC A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  4636 0000C3C1 09C0                <1> 	or	eax, eax
  4637 0000C3C3 741A                <1> 	jz	short loc_createfile_stc_retn_pop_eax
  4638 0000C3C5 8A3D[465F0100]      <1> 	mov	bh, [Current_Drv]
  4639 0000C3CB B301                <1> 	mov	bl, 01h ; BL = 1 -> add clusters
  4640                              <1> 	; NOTE: EAX value will be added to Free Cluster Count
  4641                              <1> 	; (If EAX value is negative, Free Cluster Count will be decreased)
  4642 0000C3CD E8AE060000          <1>   	call	calculate_fat_freespace
  4643                              <1>         ; ESI = Logical DOS Drive Description Table Address 
  4644                              <1>         ;jc	short loc_createfile_stc_retn_pop_eax_cf
  4645 0000C3D2 21C9                <1> 	and	ecx, ecx ; cx = 0 -> valid free sector count
  4646 0000C3D4 7409                <1> 	jz	short loc_createfile_stc_retn_pop_eax
  4647                              <1> 
  4648                              <1> loc_createfile_stc_retn_recalc_FAT_freespace:
  4649 0000C3D6 66BB00FF            <1> 	mov	bx, 0FF00h ; bh = 0FFh -> 
  4650                              <1> 	; ESI = Logical DOS Drv DT Addr
  4651                              <1> 	; BL = 0 -> Recalculate 
  4652 0000C3DA E8A1060000          <1> 	call	calculate_fat_freespace
  4653                              <1> 
  4654                              <1> loc_createfile_stc_retn_pop_eax:
  4655 0000C3DF 58                  <1> 	pop	eax
  4656 0000C3E0 9D                  <1> 	popf
  4657 0000C3E1 7218                <1> 	jc	short loc_createfile_retn
  4658                              <1> 
  4659                              <1> loc_createfile_retn_fcluster:
  4660 0000C3E3 A1[946A0100]        <1> 	mov	eax, [createfile_FFCluster]
  4661 0000C3E8 BB[906A0100]        <1> 	mov	ebx, createfile_size
  4662                              <1> 	;movzx	ecx, byte [esi+LD_BPB+SecPerClust]
  4663 0000C3ED 0FB60D[A56A0100]    <1> 	movzx	ecx, byte [createfile_SecPerClust] ; 23/03/2016
  4664 0000C3F4 0FB715[A66A0100]    <1> 	movzx	edx, word [createfile_DirIndex]
  4665                              <1> 
  4666                              <1> loc_createfile_retn:
  4667 0000C3FB C3                  <1> 	retn
  4668                              <1> 
  4669                              <1> create_fs_file:
  4670                              <1> 	; temporary (21/03/2016)
  4671 0000C3FC C3                  <1> 	retn
  4672                              <1> 
  4673                              <1> delete_fs_file:
  4674                              <1> 	; temporary (28/02/2016)
  4675 0000C3FD C3                  <1> 	retn
  4676                              <1> 
  4677                              <1> rename_fs_file_or_directory:
  4678 0000C3FE C3                  <1> 	retn
  4679                              <1> 
  4680                              <1> make_fs_directory:
  4681                              <1> 	; temporary (21/02/2016)
  4682 0000C3FF C3                  <1> 	retn
  4683                              <1> 
  4684                              <1> add_new_fs_section:
  4685                              <1> 	; temporary (11/03/2016)
  4686 0000C400 C3                  <1> 	retn
  4687                              <1> 
  4688                              <1> delete_fs_directory_entry:
  4689                              <1> 	; temporary (11/03/2016)
  4690 0000C401 C3                  <1> 	retn
  4691                              <1> 
  4692                              <1> csftdf2_read_fs_file_sectors:
  4693                              <1> 	; temporary (19/03/2016)
  4694 0000C402 C3                  <1> 	retn
  4695                              <1> 
  4696                              <1> csftdf2_write_fs_file_sectors:
  4697                              <1> 	; temporary (19/03/2016)
  4698 0000C403 C3                  <1> 	retn
  2865                                  %include 'trdosk5.s' ; 24/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - File System Procedures : trdosk5s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 23/10/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; DRV_FAT.ASM (21/08/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; DRV_FAT.ASM (c) 2005-2011 Erdogan TAN [ 07/07/2009 ] Last Update: 21/08/2011
    14                              <1> 
    15                              <1> get_next_cluster:
    16                              <1> 	; 15/10/2016
    17                              <1> 	; 23/03/2016
    18                              <1> 	; 01/02/2016 (TRDOS 386 =  TRDOS v2.0)
    19                              <1> 	; 05/07/2011
    20                              <1> 	; 07/07/2009
    21                              <1> 	; 2005
    22                              <1> 	; INPUT ->
    23                              <1> 	;	EAX = Cluster Number (32 bit)
    24                              <1> 	;	ESI = Logical DOS Drive Parameters Table
    25                              <1> 	; OUTPUT ->
    26                              <1> 	;	cf = 0 -> No Error, EAX valid
    27                              <1> 	;	cf = 1 & EAX = 0 -> End Of Cluster Chain
    28                              <1> 	;	cf = 1 & EAX > 0 -> Error
    29                              <1> 	;	ECX = Current/Previous cluster (if CF = 0)
    30                              <1> 	;	EAX = Next Cluster Number (32 bit)
    31                              <1> 	;
    32                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
    33                              <1> 
    34 0000C404 A3[56660100]        <1> 	mov	[FAT_CurrentCluster], eax
    35                              <1> check_next_cluster_fat_type:
    36 0000C409 29D2                <1> 	sub	edx, edx ; 0
    37 0000C40B 807E0302            <1>         cmp     byte [esi+LD_FATType], 2
    38 0000C40F 7250                <1> 	jb	short get_FAT12_next_cluster
    39 0000C411 0F87AF000000        <1>         ja      get_FAT32_next_cluster
    40                              <1> get_FAT16_next_cluster:
    41 0000C417 BB00030000          <1> 	mov	ebx, 300h ;768
    42 0000C41C F7F3                <1> 	div	ebx
    43                              <1> 	; EAX = Count of 3 FAT sectors
    44                              <1> 	; EDX = Cluster Offset (< 768)
    45 0000C41E 66D1E2              <1> 	shl	dx, 1 ; Multiply by 2
    46 0000C421 89D3                <1> 	mov	ebx, edx ; Byte Offset
    47 0000C423 81C3001C0900        <1> 	add	ebx, FAT_Buffer
    48 0000C429 66BA0300            <1> 	mov	dx, 3
    49 0000C42D F7E2                <1> 	mul	edx  
    50                              <1> 	; EAX = FAT Sector (<= 256)
    51                              <1> 	; EDX = 0
    52 0000C42F 8A0E                <1> 	mov	cl, [esi+LD_Name]
    53 0000C431 803D[5A660100]00    <1> 	cmp	byte [FAT_BuffValidData], 0
    54 0000C438 0F86CC000000        <1>         jna     load_FAT_sectors0
    55 0000C43E 3A0D[5B660100]      <1> 	cmp	cl, [FAT_BuffDrvName]
    56 0000C444 0F85C0000000        <1>         jne     load_FAT_sectors0
    57 0000C44A 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
    58 0000C450 0F85BA000000        <1>         jne     load_FAT_sectors1
    59                              <1> 	;movzx	eax, word [ebx]
    60 0000C456 668B03              <1> 	mov	ax, [ebx]
    61                              <1> 	; 01/02/2016
    62                              <1> 	; DRV_FAT.ASM (21/08/2011) had a FATal bug here !
    63                              <1> 	; (cmp ah, 0Fh) ! (ax >= FF7h)
    64                              <1> 	; (how can i do a such mistake!?)
    65                              <1> 	;cmp	al, 0F7h
    66                              <1> 	;jb	short loc_pass_gnc_FAT16_eoc_check
    67                              <1> 	;cmp	ah, 0FFh
    68                              <1> 	;jb	short loc_pass_gnc_FAT16_eoc_check
    69 0000C459 6683F8F7            <1> 	cmp	ax, 0FFF7h
    70 0000C45D 725A                <1> 	jb	short loc_pass_gnc_FAT16_eoc_check
    71                              <1> 	; ax >= FFF7h (cluster 0002h to FFF6h is valid, in use)
    72 0000C45F EB56                <1> 	jmp	short loc_pass_gnc_FAT16_eoc_check_xor_eax
    73                              <1> 
    74                              <1> get_FAT12_next_cluster:
    75 0000C461 BB00040000          <1> 	mov	ebx, 400h ;1024
    76 0000C466 F7F3                <1> 	div	ebx
    77                              <1> 	; EAX = Count of 3 FAT sectors
    78                              <1> 	; EDX = Cluster Offset (< 1024)
    79 0000C468 6650                <1> 	push	ax
    80 0000C46A 66B80300            <1> 	mov	ax, 3	
    81 0000C46E 66F7E2              <1> 	mul	dx    	; Multiply by 3
    82 0000C471 66D1E8              <1> 	shr	ax, 1	; Divide by 2
    83 0000C474 6689C3              <1>         mov	bx, ax 	; Byte Offset
    84 0000C477 81C3001C0900        <1> 	add	ebx, FAT_Buffer
    85 0000C47D 6658                <1> 	pop	ax
    86 0000C47F 66BA0300            <1> 	mov	dx, 3
    87 0000C483 F7E2                <1> 	mul	edx 
    88                              <1> 	; EAX = FAT Sector (<= 12)
    89                              <1> 	; EDX = 0
    90 0000C485 8A0E                <1> 	mov	cl, [esi+LD_Name]
    91 0000C487 803D[5A660100]00    <1> 	cmp	byte [FAT_BuffValidData], 0
    92 0000C48E 767A                <1> 	jna	short load_FAT_sectors0
    93 0000C490 3A0D[5B660100]      <1> 	cmp	cl, [FAT_BuffDrvName]
    94 0000C496 7572                <1> 	jne	short load_FAT_sectors0
    95 0000C498 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
    96 0000C49E 7570                <1> 	jne	short load_FAT_sectors1
    97 0000C4A0 A1[56660100]        <1> 	mov	eax, [FAT_CurrentCluster]
    98 0000C4A5 66D1E8              <1> 	shr	ax, 1
    99                              <1> 	;movzx	eax, word [ebx]
   100 0000C4A8 668B03              <1> 	mov	ax, [ebx]
   101 0000C4AB 7314                <1> 	jnc	short get_FAT12_nc_even
   102 0000C4AD 66C1E804            <1> 	shr	ax, 4
   103                              <1> loc_gnc_fat12_eoc_check:
   104                              <1> 	;cmp	al, 0F7h
   105                              <1> 	;jb	short loc_pass_gnc_FAT16_eoc_check
   106                              <1> 	;cmp	ah, 0Fh
   107                              <1> 	;jb	short loc_pass_gnc_FAT16_eoc_check
   108 0000C4B1 663DF70F            <1> 	cmp	ax, 0FF7h
   109 0000C4B5 7202                <1> 	jb	short loc_pass_gnc_FAT16_eoc_check
   110                              <1> 	; ax >= FF7h (cluster 0002h to FF6h is valid, in use)
   111                              <1> 
   112                              <1> loc_pass_gnc_FAT16_eoc_check_xor_eax:
   113 0000C4B7 31C0                <1> 	xor	eax, eax ; 0
   114                              <1> loc_pass_gnc_FAT16_eoc_check:
   115                              <1> loc_pass_gnc_FAT32_eoc_check:
   116 0000C4B9 8B0D[56660100]      <1> 	mov	ecx, [FAT_CurrentCluster]
   117 0000C4BF F5                  <1> 	cmc
   118 0000C4C0 C3                  <1> 	retn
   119                              <1> 
   120                              <1> get_FAT12_nc_even:
   121 0000C4C1 80E40F              <1> 	and	ah, 0Fh
   122 0000C4C4 EBEB                <1> 	jmp	short loc_gnc_fat12_eoc_check
   123                              <1> 
   124                              <1> get_FAT32_next_cluster:
   125 0000C4C6 BB80010000          <1> 	mov	ebx, 180h ;384
   126 0000C4CB F7F3                <1> 	div	ebx
   127                              <1> 	; EAX = Count of 3 FAT sectors
   128                              <1> 	; EDX = Cluster Offset (< 384)
   129 0000C4CD 66C1E202            <1> 	shl	dx, 2	; Multiply by 4
   130 0000C4D1 89D3                <1> 	mov	ebx, edx ; Byte Offset
   131 0000C4D3 81C3001C0900        <1> 	add	ebx, FAT_Buffer
   132 0000C4D9 66BA0300            <1> 	mov	dx, 3
   133 0000C4DD F7E2                <1> 	mul	edx	
   134                              <1>         ; EAX = FAT Sector (<= 2097152) ; (FFFFFF7h * 4) / 512
   135                              <1> 	; 	for 32KB cluster size:
   136                              <1> 	;	EAX <= 1024 = (4GB / 32KB) * 4) / 512 	
   137                              <1> 	; EDX = 0
   138 0000C4DF 8A0E                <1> 	mov	cl, [esi+LD_Name]
   139 0000C4E1 803D[5A660100]00    <1> 	cmp	byte [FAT_BuffValidData], 0
   140 0000C4E8 7620                <1> 	jna	short load_FAT_sectors0
   141 0000C4EA 3A0D[5B660100]      <1> 	cmp	cl, [FAT_BuffDrvName]
   142 0000C4F0 7518                <1> 	jne	short load_FAT_sectors0
   143 0000C4F2 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector] ; 0, 3, 6, 9 ...
   144 0000C4F8 7516                <1> 	jne	short load_FAT_sectors1
   145 0000C4FA 8B03                <1> 	mov	eax, [ebx]
   146 0000C4FC 25FFFFFF0F          <1>  	and	eax, 0FFFFFFFh ; 28 bit Cluster
   147 0000C501 3DF7FFFF0F          <1> 	cmp	eax, 0FFFFFF7h
   148 0000C506 72B1                <1> 	jb	short loc_pass_gnc_FAT32_eoc_check
   149                              <1> 	; eax >= FFFFFF7h (cluster 0002h to FFFFFF6h is valid)
   150 0000C508 EBAD                <1> 	jmp	short loc_pass_gnc_FAT16_eoc_check_xor_eax
   151                              <1> 
   152                              <1> load_FAT_sectors0:
   153 0000C50A 880D[5B660100]      <1> 	mov	[FAT_BuffDrvName], cl
   154                              <1> load_FAT_sectors1:
   155 0000C510 A3[5E660100]        <1> 	mov	[FAT_BuffSector], eax
   156 0000C515 89C3                <1> 	mov	ebx, eax
   157 0000C517 034660              <1>         add     eax, [esi+LD_FATBegin]
   158 0000C51A 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
   159 0000C51E 7706                <1>         ja      short load_FAT_sectors3
   160 0000C520 0FB74E1C            <1> 	movzx	ecx, word [esi+LD_BPB+BPB_FATSz16]
   161 0000C524 EB03                <1> 	jmp	short load_FAT_sectors4
   162                              <1> load_FAT_sectors3:
   163 0000C526 8B4E2A              <1> 	mov	ecx, [esi+LD_BPB+BPB_FATSz32]
   164                              <1> load_FAT_sectors4:
   165 0000C529 29D9                <1> 	sub	ecx, ebx ; [FAT_BuffSector]
   166 0000C52B 83F903              <1>         cmp     ecx, 3
   167 0000C52E 7605                <1>         jna     short load_FAT_sectors5
   168 0000C530 B903000000          <1> 	mov	ecx, 3
   169                              <1> load_FAT_sectors5:
   170 0000C535 BB001C0900          <1> 	mov	ebx, FAT_Buffer
   171 0000C53A E882380000          <1> 	call	disk_read
   172 0000C53F 730D                <1> 	jnc	short load_FAT_sectors_ok
   173                              <1> 	; 15/10/2016 (15h -> 17)
   174                              <1> 	; 23/03/2016 (15h)
   175 0000C541 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error
   176 0000C546 C605[5A660100]00    <1> 	mov	byte [FAT_BuffValidData], 0
   177 0000C54D C3                  <1> 	retn
   178                              <1> load_FAT_sectors_ok:
   179 0000C54E C605[5A660100]01    <1> 	mov	byte [FAT_BuffValidData], 1
   180 0000C555 A1[56660100]        <1> 	mov	eax, [FAT_CurrentCluster]
   181 0000C55A E9AAFEFFFF          <1>         jmp     check_next_cluster_fat_type
   182                              <1> 
   183                              <1> load_FAT_root_directory:
   184                              <1> 	; 23/10/2016
   185                              <1> 	; 15/10/2016
   186                              <1> 	; 07/02/2016
   187                              <1> 	; 02/02/2016
   188                              <1> 	; 01/02/2016 (TRDOS 386 =  TRDOS v2.0)
   189                              <1> 	; 21/05/2011
   190                              <1> 	; 22/08/2009
   191                              <1> 	;
   192                              <1> 	; INPUT ->
   193                              <1> 	;	ESI = Logical DOS Drive Description Table
   194                              <1> 	; OUTPUT ->
   195                              <1> 	;	cf = 1 -> Root directory could not be loaded
   196                              <1> 	;	    EAX > 0 -> Error number
   197                              <1> 	;	cf = 0 -> EAX = 0
   198                              <1> 	;	ECX = Directory buffer size in sectors (CL)
   199                              <1> 	;	EBX = Directory buffer address
   200                              <1> 	; 	NOTE: DirBuffer_Size is in bytes ! (word)
   201                              <1> 	;
   202                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
   203                              <1> 
   204                              <1> 	; NOTE: Only for FAT12 and FAT16 file systems !
   205                              <1> 	; (FAT32 fs root dir must be loaded as sub directory)
   206                              <1> 
   207 0000C55F 8A1E                <1> 	mov	bl, [esi+LD_Name]
   208 0000C561 8A7E03              <1> 	mov	bh, [esi+LD_FATType]
   209                              <1> 
   210                              <1> 	;mov	[DirBuff_DRV], bl
   211                              <1> 	;mov	[DirBuff_FATType], bh
   212 0000C564 66891D[6A660100]    <1> 	mov	[DirBuff_DRV], bx
   213                              <1> 	
   214                              <1> 	;cmp	bh, 2
   215                              <1> 	;ja	short load_FAT32_root_dir0 ; FAT32 root dir
   216                              <1> 
   217                              <1> load_FAT_root_dir0: ; 23/10/2016
   218 0000C56B 0FB75617            <1> 	movzx	edx, word [esi+LD_BPB+RootDirEnts]
   219                              <1> 
   220                              <1> 	;or	dx, dx ; 0 for FAT32 file systems
   221                              <1> 	;jz	short load_FAT32_root_dir0 ; FAT32 root dir
   222                              <1> 
   223 0000C56F 6681FA0002          <1> 	cmp	dx, 512 ; Number of Root Dir Entries
   224 0000C574 7414                <1> 	je	short lrd_mov_ecx_32
   225 0000C576 89D0                <1> 	mov	eax, edx
   226                              <1> 	; 23/10/2016
   227 0000C578 89C1                <1> 	mov	ecx, eax
   228 0000C57A 6683C10F            <1> 	add	cx, 15 ; round up 
   229 0000C57E 66C1E904            <1> 	shr	cx, 4  ; 16 entries per sector (512/32)
   230                              <1> 	; ecx = Root directory size in sectors
   231 0000C582 66C1E005            <1> 	shl	ax, 5 ; Root directory size in bytes
   232 0000C586 664A                <1> 	dec	dx    ; Last entry number of root dir
   233                              <1> 	; cx = Dir Buffer sector count             
   234 0000C588 EB0B                <1> 	jmp	short lrd_check_dir_buffer
   235                              <1> 
   236                              <1> lrd_mov_ecx_32:
   237 0000C58A B920000000          <1> 	mov	ecx, 32
   238 0000C58F 664A                <1> 	dec	dx ; 511
   239 0000C591 66B80040            <1> 	mov	ax, 32*512 
   240                              <1>  
   241                              <1> lrd_check_dir_buffer:
   242 0000C595 29DB                <1> 	sub	ebx, ebx ; 0
   243 0000C597 881D[6C660100]      <1> 	mov	[DirBuff_ValidData], bl ; 0
   244 0000C59D 668915[6F660100]    <1> 	mov	[DirBuff_LastEntry], dx
   245 0000C5A4 891D[71660100]      <1> 	mov	[DirBuff_Cluster], ebx ; 0
   246 0000C5AA 66A3[75660100]      <1> 	mov	[DirBuffer_Size], ax
   247                              <1> 
   248 0000C5B0 8B4664              <1> 	mov	eax, [esi+LD_ROOTBegin]
   249                              <1> read_directory:
   250 0000C5B3 BB00000800          <1> 	mov	ebx, Directory_Buffer
   251 0000C5B8 51                  <1> 	push	ecx ; Directory buffer sector count
   252 0000C5B9 53                  <1> 	push	ebx
   253 0000C5BA E802380000          <1> 	call	disk_read
   254 0000C5BF 5B                  <1> 	pop	ebx
   255 0000C5C0 720B                <1> 	jc	short load_DirBuff_error
   256                              <1> 
   257                              <1> validate_DirBuff_and_return:
   258 0000C5C2 59                  <1> 	pop	ecx ; Number of loaded sectors
   259 0000C5C3 C605[6C660100]01    <1> 	mov	byte [DirBuff_ValidData], 1
   260 0000C5CA 31C0                <1> 	xor	eax, eax ; 0 = no error
   261 0000C5CC C3                  <1> 	retn
   262                              <1> 
   263                              <1> load_DirBuff_error:
   264 0000C5CD 89C8                <1> 	mov	eax, ecx ; remaining sectors
   265 0000C5CF 59                  <1> 	pop	ecx ; sector count
   266 0000C5D0 29C1                <1> 	sub	ecx, eax ; Number of loaded sectors
   267                              <1> 	; 15/10/2016 (15h -> 17)
   268 0000C5D2 B811000000          <1> 	mov	eax, 17 ; DRV NOT READY OR READ ERROR !
   269 0000C5D7 F9                  <1> 	stc
   270 0000C5D8 C3                  <1>         retn
   271                              <1> 
   272                              <1> load_FAT32_root_directory:
   273                              <1> 	; 02/02/2016 (TRDOS 386 =  TRDOS v2.0)
   274                              <1> 	;
   275                              <1> 	; INPUT ->
   276                              <1> 	;	ESI = Logical DOS Drive Description Table
   277                              <1> 	; OUTPUT ->
   278                              <1> 	;	cf = 1 -> Root directory could not be loaded
   279                              <1> 	;	    EAX > 0 -> Error number
   280                              <1> 	;	cf = 0 -> EAX = 0
   281                              <1> 	;	ECX = Directory buffer size in sectors (CL)
   282                              <1> 	;	EBX = Directory buffer address
   283                              <1> 	; 	NOTE: DirBuffer_Size is in bytes ! (word)
   284                              <1> 	;
   285                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
   286                              <1> 
   287                              <1> 
   288 0000C5D9 8A1E                <1> 	mov	bl, [esi+LD_Name]
   289 0000C5DB 8A7E03              <1> 	mov	bh, [esi+LD_FATType]
   290                              <1> 
   291                              <1> 	;mov	[DirBuff_DRV], bl
   292                              <1> 	;mov	[DirBuff_FATType], bh
   293 0000C5DE 66891D[6A660100]    <1> 	mov	[DirBuff_DRV], bx
   294                              <1> 
   295                              <1> load_FAT32_root_dir0:
   296 0000C5E5 8B4632              <1> 	mov	eax, [esi+LD_BPB+FAT32_RootFClust]
   297 0000C5E8 EB0C                <1> 	jmp	short load_FAT_sub_dir0
   298                              <1> 	
   299                              <1> load_FAT_sub_directory:
   300                              <1> 	; 01/02/2016 (TRDOS 386 =  TRDOS v2.0)
   301                              <1> 	; 05/07/2011
   302                              <1> 	; 23/08/2009
   303                              <1> 	;
   304                              <1> 	; INPUT ->
   305                              <1> 	;	ESI = Logical DOS Drive Description Table
   306                              <1> 	;	EAX = Cluster Number
   307                              <1> 	; OUTPUT ->
   308                              <1> 	;	cf = 1 -> Sub directory could not be loaded
   309                              <1> 	;	    EAX > 0 -> Error number
   310                              <1> 	;	cf = 0 -> EAX = 0
   311                              <1> 	;	ECX = Directory buffer size in sectors (CL)
   312                              <1> 	;	EBX = Directory buffer address
   313                              <1> 	;
   314                              <1> 	; 	NOTE: DirBuffer_Size is in bytes ! (word)
   315                              <1> 	;
   316                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
   317                              <1> 
   318 0000C5EA 8A1E                <1> 	mov	bl, [esi+LD_Name]
   319 0000C5EC 8A7E03              <1> 	mov	bh, [esi+LD_FATType]
   320                              <1> 
   321                              <1> 	;mov	[DirBuff_DRV], bl
   322                              <1> 	;mov	[DirBuff_FATType], bh
   323 0000C5EF 66891D[6A660100]    <1> 	mov	[DirBuff_DRV], bx
   324                              <1> 
   325                              <1> load_FAT_sub_dir0:
   326 0000C5F6 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+SecPerClust]
   327                              <1> 
   328 0000C5FA 882D[6C660100]      <1> 	mov	[DirBuff_ValidData], ch ; 0
   329 0000C600 A3[71660100]        <1> 	mov	[DirBuff_Cluster], eax
   330                              <1> 
   331 0000C605 0FB74611            <1> 	movzx	eax, word [esi+LD_BPB+BytesPerSec]
   332 0000C609 F7E1                <1> 	mul	ecx
   333 0000C60B C1E805              <1> 	shr	eax, 5 ; directory entry count (dir size / 32)
   334 0000C60E 6648                <1> 	dec	ax ; last entry
   335 0000C610 66A3[6F660100]      <1> 	mov	[DirBuff_LastEntry], ax
   336                              <1> 
   337 0000C616 A1[71660100]        <1> 	mov	eax, [DirBuff_Cluster]
   338 0000C61B 83E802              <1> 	sub	eax, 2
   339 0000C61E F7E1                <1> 	mul	ecx
   340 0000C620 034668              <1> 	add	eax, [esi+LD_DATABegin]
   341                              <1> 	; ecx = sector per cluster (dir buffer size = 32 sectors)
   342 0000C623 EB8E                <1> 	jmp	short read_directory
   343                              <1> 
   344                              <1> ; DRV_FS.ASM
   345                              <1> 
   346                              <1> load_current_FS_directory:
   347 0000C625 C3                  <1> 	retn
   348                              <1> load_FS_root_directory:
   349 0000C626 C3                  <1> 	retn
   350                              <1> load_FS_sub_directory:
   351 0000C627 C3                  <1> 	retn
   352                              <1> 
   353                              <1> read_cluster:
   354                              <1> 	; 15/10/2016
   355                              <1> 	; 18/03/2016
   356                              <1> 	; 16/03/2016
   357                              <1> 	; 17/02/2016
   358                              <1> 	; 15/02/2016 (TRDOS 386 =  TRDOS v2.0)
   359                              <1> 	;
   360                              <1> 	; INPUT ->
   361                              <1> 	;	EAX = Cluster Number (Sector index for SINGLIX FS)
   362                              <1> 	;	ESI = Logical DOS Drive Description Table address
   363                              <1> 	;	EBX = Cluster (File R/W) Buffer address (max. 64KB)
   364                              <1> 	;	Only for SINGLIX FS:
   365                              <1> 	;	EDX = File Number (The 1st FDT address) 
   366                              <1> 	; OUTPUT ->
   367                              <1> 	;	cf = 1 -> Cluster can not be loaded at the buffer
   368                              <1> 	;	    EAX > 0 -> Error number
   369                              <1> 	;	cf = 0 -> Cluster has been loaded at the buffer
   370                              <1> 	;
   371                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
   372                              <1> 	
   373 0000C628 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+BPB_SecPerClust] 
   374                              <1> 	; CL = 1 = [esi+LD_FS_Reserved2] ; SectPerClust for Singlix FS
   375                              <1> 
   376                              <1> read_file_sectors: ; 16/03/2016
   377 0000C62C 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
   378 0000C630 761C                <1> 	jna	short read_fs_cluster
   379                              <1> 
   380                              <1> read_fat_file_sectors: ; 18/03/2016
   381 0000C632 83E802              <1> 	sub	eax, 2 ; Beginning cluster number is always 2
   382 0000C635 0FB65613            <1> 	movzx	edx, byte [esi+LD_BPB+BPB_SecPerClust] ; 18/03/2016 
   383 0000C639 F7E2                <1> 	mul	edx
   384 0000C63B 034668              <1> 	add	eax, [esi+LD_DATABegin] ; absolute address of the cluster
   385                              <1> 
   386                              <1> 	; EAX = Disk sector address
   387                              <1> 	; ECX = Sector count
   388                              <1> 	; EBX = Buffer address
   389                              <1> 	; (EDX = 0)
   390                              <1> 	; ESI = Logical DOS drive description table address	
   391                              <1> 
   392 0000C63E E87E370000          <1> 	call	disk_read
   393 0000C643 7306                <1> 	jnc	short rclust_retn
   394                              <1> 	
   395                              <1> 	; 15/10/2016 (15h -> 17)
   396 0000C645 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error !
   397 0000C64A C3                  <1> 	retn
   398                              <1> 
   399                              <1> rclust_retn:
   400 0000C64B 29C0                <1> 	sub	eax, eax ; 0
   401 0000C64D C3                  <1> 	retn
   402                              <1> 
   403                              <1> read_fs_cluster:
   404                              <1> 	; 15/02/2016 (TRDOS 386 =  TRDOS v2.0)
   405                              <1> 	; Singlix FS
   406                              <1> 	
   407                              <1> 	; EAX = Cluster number is sector index number of the file (eax)
   408                              <1> 	
   409                              <1> 	; EDX = File number is the first File Descriptor Table address 
   410                              <1> 	;	of the file. (Absolute address of the FDT).
   411                              <1> 	
   412                              <1> 	; eax = sector index (0 for the first sector)
   413                              <1> 	; edx = FDT0 address
   414                              <1> 		; 64 KB buffer = 128 sectors (limit) 
   415 0000C64E B980000000          <1> 	mov	ecx, 128 ; maximum count of sectors (before eof) 
   416 0000C653 E801000000          <1> 	call	read_fs_sectors
   417 0000C658 C3                  <1> 	retn
   418                              <1> 
   419                              <1> read_fs_sectors:
   420                              <1> 	; 15/02/2016 (TRDOS 386 =  TRDOS v2.0)
   421 0000C659 F9                  <1> 	stc
   422 0000C65A C3                  <1> 	retn
   423                              <1> 
   424                              <1> get_first_free_cluster:
   425                              <1> 	; 02/03/2016
   426                              <1> 	; 21/02/2016 (TRDOS 386 =  TRDOS v2.0)
   427                              <1> 	; 26/10/2010 (DRV_FAT.ASM, 'proc_get_first_free_cluster')
   428                              <1> 	; 10/07/2010
   429                              <1> 	; INPUT ->
   430                              <1> 	;	ESI = Logical DOS Drive Description Table address
   431                              <1> 	; OUTPUT ->
   432                              <1> 	;	cf = 1 -> Error code in AL (EAX)
   433                              <1> 	;	cf = 0 -> 
   434                              <1> 	;	  EAX = Cluster number 
   435                              <1> 	;	  If EAX = FFFFFFFFh -> no free space
   436                              <1> 	;	If the drive has FAT32 fs:
   437                              <1> 	;	  EBX = FAT32 FSI sector buffer address (if > 0)
   438                              <1> 
   439 0000C65B 8B4678              <1> 	mov	eax, [esi+LD_Clusters]
   440 0000C65E 40                  <1> 	inc	eax ; add eax, 1
   441 0000C65F A3[F4680100]        <1> 	mov	[gffc_last_free_cluster], eax
   442                              <1> 
   443 0000C664 31DB                <1> 	xor	ebx, ebx ; 0 ; 02/03/2016
   444                              <1> 
   445 0000C666 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
   446 0000C66A 760E                <1> 	jna	short loc_gffc_get_first_fat_free_cluster0
   447                              <1> 
   448                              <1> loc_gffc_get_first_fat32_free_cluster:
   449                              <1> 	; 02/03/2016
   450 0000C66C E844060000          <1> 	call	get_fat32_fsinfo_sector_parms
   451 0000C671 7207                <1> 	jc	short loc_gffc_get_first_fat_free_cluster0 
   452                              <1> 
   453                              <1> loc_gffc_check_fsinfo_parms:
   454                              <1> 	;;mov	ebx, DOSBootSectorBuff
   455                              <1> 	;cmp	dword [ebx], 41615252h
   456                              <1> 	;jne	short loc_gffc_fat32_fsinfo_err
   457                              <1> 	;cmp	dword [ebx+484], 61417272h
   458                              <1> 	;jne	short loc_gffc_fat32_fsinfo_err
   459                              <1> 	;mov	eax, [ebx+492] ; FSI_Next_Free
   460                              <1> 	;EAX = First free cluster 
   461                              <1> 	;(from FAT32 FSInfo sector)
   462 0000C673 89D0                <1> 	mov	eax, edx ; FSI_Next_Free (First Free Cluster)
   463 0000C675 83F8FF              <1> 	cmp	eax, 0FFFFFFFFh ; invalid (unknown) !
   464 0000C678 7205                <1> 	jb	short loc_gffc_get_first_fat_free_cluster1
   465                              <1> 
   466                              <1> 	; Start from the 1st cluster of the FAT(32) file system
   467                              <1> loc_gffc_get_first_fat_free_cluster0:
   468 0000C67A B802000000          <1> 	mov	eax, 2
   469                              <1> 	;xor	edx, edx
   470                              <1> 
   471                              <1> loc_gffc_get_first_fat_free_cluster1:
   472 0000C67F 53                  <1> 	push	ebx ; 02/03/2016 
   473                              <1> 
   474                              <1> loc_gffc_get_first_fat_free_cluster2:   
   475 0000C680 A3[F0680100]        <1> 	mov	[gffc_first_free_cluster], eax
   476 0000C685 A3[EC680100]        <1> 	mov	[gffc_next_free_cluster], eax
   477                              <1> 
   478                              <1> 	; EBX = FAT32 FSINFO sector buffer address
   479                              <1> 	; (EBX = 0, if the drive has not got FAT32 fs or
   480                              <1> 	; FAT32 FSINFO sector buffer is invalid.)
   481                              <1> 
   482                              <1> loc_gffc_get_first_fat_free_cluster3:
   483 0000C68A E875FDFFFF          <1> 	call	get_next_cluster
   484 0000C68F 7307                <1> 	jnc	short loc_gffc_get_first_fat_free_cluster4
   485 0000C691 09C0                <1> 	or	eax, eax
   486 0000C693 740B                <1> 	jz	short loc_gffc_first_free_fat_cluster_next
   487 0000C695 5B                  <1> 	pop	ebx ; 02/03/2016
   488 0000C696 F5                  <1> 	cmc 	; stc
   489 0000C697 C3                  <1> 	retn
   490                              <1> 
   491                              <1> loc_gffc_get_first_fat_free_cluster4:
   492 0000C698 21C0                <1> 	and	eax, eax ; next cluster value
   493 0000C69A 7504                <1> 	jnz	short loc_gffc_first_free_fat_cluster_next
   494 0000C69C 89C8                <1> 	mov	eax, ecx ; current (previous cluster) value
   495 0000C69E EB22                <1> 	jmp	short loc_gffc_check_for_set
   496                              <1>  
   497                              <1> loc_gffc_first_free_fat_cluster_next:
   498 0000C6A0 A1[EC680100]        <1> 	mov	eax, [gffc_next_free_cluster]
   499 0000C6A5 3B05[F4680100]      <1> 	cmp	eax, [gffc_last_free_cluster]
   500 0000C6AB 7308                <1> 	jnb	short retn_stc_from_get_first_free_cluster
   501                              <1> pass_gffc_last_cluster_eax_check:
   502 0000C6AD 40                  <1> 	inc	eax ; add eax, 1
   503 0000C6AE A3[EC680100]        <1> 	mov	[gffc_next_free_cluster], eax
   504 0000C6B3 EBD5                <1> 	jmp	short loc_gffc_get_first_fat_free_cluster3
   505                              <1> 
   506                              <1> retn_stc_from_get_first_free_cluster:
   507 0000C6B5 A1[F0680100]        <1> 	mov	eax, [gffc_first_free_cluster]
   508 0000C6BA 83F802              <1> 	cmp	eax, 2
   509 0000C6BD 7709                <1> 	ja	short loc_gffc_check_previous_clusters
   510 0000C6BF 29C0                <1> 	sub	eax, eax
   511 0000C6C1 48                  <1> 	dec	eax ; FFFFFFFFh
   512                              <1> 
   513                              <1> loc_gffc_check_for_set:
   514                              <1> 	; 02/03/2016
   515 0000C6C2 5B                  <1> 	pop	ebx
   516                              <1> 
   517                              <1> 	; EBX = FAT32 FSINFO sector buffer address
   518                              <1> 	; (EBX = 0, if the drive has not got FAT32 fs or
   519                              <1> 	; FAT32 FSINFO sector buffer is invalid.)
   520                              <1> 
   521 0000C6C3 09DB                <1> 	or	ebx, ebx
   522 0000C6C5 750E                <1> 	jnz	short loc_gffc_set_ffree_fat32_cluster
   523                              <1> 
   524                              <1> 	;cmp	byte [esi+LD_FATType], 3
   525                              <1> 	;jnb	short loc_gffc_set_ffree_fat32_cluster
   526                              <1> 
   527                              <1> 	;xor	ebx, ebx ; 0
   528                              <1> 
   529                              <1> loc_gffc_retn:
   530 0000C6C7 C3                  <1> 	retn
   531                              <1> 
   532                              <1> loc_gffc_check_previous_clusters:
   533 0000C6C8 48                  <1> 	dec	eax ; sub eax, 1
   534 0000C6C9 A3[F4680100]        <1> 	mov	[gffc_last_free_cluster], eax 
   535 0000C6CE B802000000          <1> 	mov	eax, 2
   536                              <1> 	;xor	edx, edx
   537 0000C6D3 EBAB                <1> 	jmp	short loc_gffc_get_first_fat_free_cluster2
   538                              <1> 
   539                              <1> loc_gffc_set_ffree_fat32_cluster:
   540                              <1> 	;call	set_first_free_cluster
   541                              <1> 	;retn
   542                              <1> 	;jmp	short set_first_free_cluster	
   543                              <1> 
   544                              <1> set_first_free_cluster:
   545                              <1> 	; 15/10/2016
   546                              <1> 	; 23/03/2016
   547                              <1> 	; 02/03/2016
   548                              <1> 	; 29/02/2016
   549                              <1> 	; 26/02/2016
   550                              <1> 	; 21/02/2016 (TRDOS 386 =  TRDOS v2.0)
   551                              <1> 	; 21/08/2011 (DRV_FAT.ASM, 'proc_set_first_free_cluster')
   552                              <1> 	; 11/07/2010
   553                              <1> 	; INPUT -> 
   554                              <1> 	;	ESI = Logical DOS Drive Description Table address
   555                              <1> 	;	EAX = First free cluster
   556                              <1> 	;	EBX = FSINFO sector buffer address
   557                              <1> 	;  	;;If EBX > 0, it is FSINFO sector buffer address
   558                              <1> 	;	;;EBX = 0, if FSINFO sector is not loaded
   559                              <1> 	; OUTPUT->
   560                              <1> 	;	ESI = Logical DOS Drive Description Table address
   561                              <1> 	;  	If EBX > 0, it is FSINFO sector buffer address
   562                              <1> 	;	EBX = 0, if FSINFO sector could not be loaded
   563                              <1> 	; 	CF = 1 -> Error code in AL (EAX)
   564                              <1> 	;	CF = 0 -> first free cluster is successfully updated 
   565                              <1> 
   566                              <1> 	;cmp	byte [esi+LD_FATType], 3
   567                              <1> 	;jb	short loc_sffc_invalid_drive
   568                              <1> 
   569                              <1> 	; Save First Free Cluster value for 'update_cluster'
   570 0000C6D5 89463E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], eax ; First free Cluster	
   571                              <1> 
   572                              <1> 	;or	ebx, ebx
   573                              <1> 	;jnz	short loc_sffc_read_fsinfo_sector
   574                              <1> 
   575 0000C6D8 813B52526141        <1> 	cmp     dword [ebx], 41615252h
   576 0000C6DE 7540                <1> 	jne	short loc_sffc_read_fsinfo_sector
   577 0000C6E0 81BBE4010000727241- <1> 	cmp	dword [ebx+484], 61417272h
   577 0000C6E9 61                  <1>
   578 0000C6EA 7534                <1> 	jne	short loc_sffc_read_fsinfo_sector
   579                              <1> 
   580 0000C6EC 3B83EC010000        <1> 	cmp	eax, [ebx+492]  ; FSI_Next_Free
   581 0000C6F2 741F                <1> 	je	short loc_sffc_retn
   582                              <1> 
   583                              <1> loc_sffc_write_fsinfo_sector:
   584                              <1> 	; EBX = FSINFO sector buffer
   585                              <1> 	; [CFS_FAT32FSINFOSEC] is set in 'get_fat32_fsinfo_sector_parms'
   586 0000C6F4 8983EC010000        <1> 	mov	[ebx+492], eax
   587 0000C6FA A1[04690100]        <1> 	mov	eax, [CFS_FAT32FSINFOSEC] 
   588 0000C6FF B901000000          <1> 	mov	ecx, 1
   589 0000C704 53                  <1> 	push	ebx
   590 0000C705 E8A8360000          <1> 	call	disk_write
   591 0000C70A 7208                <1> 	jc      short loc_sffc_read_fsinfo_sector_err1
   592 0000C70C 5B                  <1> 	pop	ebx
   593                              <1> 
   594 0000C70D 8B83EC010000        <1> 	mov	eax, [ebx+492] ; First (Next) Free Cluster
   595                              <1> 
   596                              <1> loc_sffc_retn:
   597 0000C713 C3                  <1> 	retn
   598                              <1> 
   599                              <1> ;loc_sffc_invalid_drive:
   600                              <1> ;	mov	eax, 0Fh ; MSDOS Error : Invalid drive
   601                              <1> ;	push	edx
   602                              <1> 
   603                              <1> loc_sffc_read_fsinfo_sector_err1:
   604 0000C714 BB00000000          <1> 	mov	ebx, 0
   605                              <1> 	; 15/10/2016 (1Dh -> 18)
   606                              <1> 	; 23/03/2016 (1Dh)
   607 0000C719 B812000000          <1> 	mov	eax, 18 ; Drive not ready or write error
   608                              <1> 
   609                              <1> loc_sffc_read_fsinfo_sector_err2:
   610 0000C71E 5A                  <1> 	pop	edx
   611 0000C71F C3                  <1> 	retn
   612                              <1> 	
   613                              <1> loc_sffc_read_fsinfo_sector:
   614 0000C720 50                  <1> 	push	eax
   615                              <1> 
   616 0000C721 E88F050000          <1> 	call	get_fat32_fsinfo_sector_parms
   617 0000C726 72F6                <1> 	jc	short loc_sffc_read_fsinfo_sector_err2
   618                              <1> 
   619 0000C728 58                  <1> 	pop	eax
   620                              <1> 	; EDX = First (Next) Free Cluster value from FSINFO sector
   621                              <1> 	; EAX = First Free Cluster value from 'get_next_cluster'
   622                              <1> 	; (edx = old value)
   623 0000C729 39D0                <1> 	cmp	eax, edx ; First free Cluster (eax = new value) 
   624 0000C72B 75C7                <1> 	jne	short loc_sffc_write_fsinfo_sector
   625                              <1> 
   626 0000C72D C3                  <1> 	retn	
   627                              <1> 
   628                              <1> update_cluster:
   629                              <1> 	; 23/10/2016
   630                              <1> 	; 23/03/2016
   631                              <1> 	; 02/03/2016
   632                              <1> 	; 01/03/2016
   633                              <1> 	; 29/02/2016
   634                              <1> 	; 27/02/2016
   635                              <1> 	; 26/02/2016
   636                              <1> 	; 22/02/2016 (TRDOS 386 =  TRDOS v2.0)
   637                              <1> 	; 11/08/2011  
   638                              <1> 	; 09/02/2005
   639                              <1> 	; INPUT ->
   640                              <1> 	;	EAX = Cluster Number
   641                              <1> 	;	ECX = New Cluster Value
   642                              <1> 	;	ESI = Logical Dos Drive Parameters Table
   643                              <1> 	;
   644                              <1> 	;	/// dword [FAT_ClusterCounter] ///
   645                              <1> 	;
   646                              <1> 	; OUTPUT ->
   647                              <1> 	;	cf = 0 -> No Error, EAX is valid
   648                              <1> 	;	cf = 1 & EAX = 0 -> End Of Cluster Chain
   649                              <1> 	; 	cf = 1 & EAX > 0 -> Error
   650                              <1> 	;		(ECX -> any value)
   651                              <1> 	; 	EAX = Next Cluster
   652                              <1> 	;	ECX = New Cluster Value
   653                              <1> 	;
   654                              <1> 	;	/// [FAT_ClusterCounter] is updated,
   655                              <1> 	;	/// decreased when a free cluster is assigned,
   656                              <1> 	;	/// increased if an assigned cluster is freed.	
   657                              <1> 	;		
   658                              <1> 	;
   659                              <1> 	; (Modified registers: EAX, EBX, -ECX-, EDX)
   660                              <1> 	
   661 0000C72E A3[56660100]        <1> 	mov	[FAT_CurrentCluster], eax
   662 0000C733 890D[F8680100]      <1> 	mov	[ClusterValue], ecx
   663                              <1> 
   664                              <1> loc_update_cluster_check_fat_buffer:
   665 0000C739 8A1E                <1> 	mov	bl, [esi+LD_Name]
   666 0000C73B 381D[5B660100]      <1> 	cmp	[FAT_BuffDrvName], bl
   667 0000C741 741A                <1> 	je	short loc_update_cluster_check_fat_type
   668 0000C743 803D[5A660100]02    <1> 	cmp	byte [FAT_BuffValidData], 2
   669 0000C74A 0F84C2000000        <1>         je      loc_uc_save_fat_buffer
   670                              <1> 
   671                              <1> loc_uc_reset_fat_buffer_validation:
   672 0000C750 C605[5A660100]00    <1> 	mov	byte [FAT_BuffValidData], 0
   673                              <1> 
   674                              <1> loc_uc_check_fat_type_reset_drvname:
   675 0000C757 881D[5B660100]      <1> 	mov	[FAT_BuffDrvName], bl
   676                              <1> 
   677                              <1> loc_update_cluster_check_fat_type:
   678 0000C75D 29D2                <1> 	sub	edx, edx ; 26/02/2016
   679 0000C75F 8A5E03              <1> 	mov	bl, [esi+LD_FATType]
   680 0000C762 83F802              <1> 	cmp	eax, 2
   681 0000C765 0F82BE000000        <1>         jb      update_cluster_inv_data
   682 0000C76B 80FB02              <1> 	cmp	bl, 2 
   683 0000C76E 0F877A010000        <1>         ja      update_fat32_cluster
   684                              <1> 	;cmp	bl, 1
   685                              <1> 	;jb	short update_cluster_inv_data
   686 0000C774 8B4E78              <1> 	mov	ecx, [esi+LD_Clusters]
   687 0000C777 41                  <1> 	inc	ecx  
   688 0000C778 890D[66660100]      <1> 	mov	[LastCluster], ecx
   689 0000C77E 39C8                <1> 	cmp	eax, ecx ; dword [LastCluster]
   690 0000C780 0F87A6000000        <1>         ja      return_uc_fat_stc
   691                              <1> 	; TRDOS v1 has a FATal bug here ! 
   692                              <1> 		; or bl, bl ; cmp bl, 0
   693                              <1> 		; jz short update_fat12_cluster
   694                              <1> 	; !! It would destroy FAT12 floppy disk fs here !!
   695                              <1> 	; ('A:' disks of TRDOS v1 operating system project
   696                              <1> 	; had 'singlix fs', so, I could not differ this mistake
   697                              <1> 	; on a drive 'A:')
   698 0000C786 80FB01              <1> 	cmp	bl, 1 ; correct comparison is this !
   699 0000C789 0F86A2000000        <1>         jna     update_fat12_cluster 
   700                              <1> 
   701                              <1> update_fat16_cluster:
   702                              <1> pass_uc_fat16_errc:
   703                              <1> 	;sub	edx, edx
   704 0000C78F BB00030000          <1> 	mov	ebx, 300h ;768
   705 0000C794 F7F3                <1> 	div	ebx
   706                              <1> 	; EAX = Count of 3 FAT sectors
   707                              <1> 	; DX = Cluster offset in FAT buffer
   708 0000C796 6689D3              <1> 	mov	bx, dx  
   709 0000C799 66D1E3              <1> 	shl	bx, 1 ; Multiply by 2
   710 0000C79C 66BA0300            <1> 	mov	dx, 3
   711 0000C7A0 F7E2                <1> 	mul	edx  
   712                              <1> 	; EAX = FAT Sector
   713                              <1> 	; EDX = 0
   714                              <1> 	; EBX = Byte offset in FAT buffer
   715 0000C7A2 8A0D[5A660100]      <1> 	mov	cl, [FAT_BuffValidData]
   716 0000C7A8 80F902              <1> 	cmp	cl, 2
   717 0000C7AB 750A                <1> 	jne	short loc_uc_check_fat16_buff_sector_load
   718                              <1> 
   719                              <1> loc_uc_check_fat16_buff_sector_save:
   720 0000C7AD 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   721 0000C7B3 755D                <1> 	jne	short loc_uc_save_fat_buffer
   722 0000C7B5 EB15                <1> 	jmp	short loc_update_fat16_cell
   723                              <1> 
   724                              <1> loc_uc_check_fat16_buff_sector_load:
   725 0000C7B7 80F901              <1> 	cmp	cl, 1 ; byte [FAT_BuffValidData]
   726 0000C7BA 0F85FB010000        <1>         jne     loc_uc_load_fat_sectors
   727 0000C7C0 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   728 0000C7C6 0F85EF010000        <1>         jne     loc_uc_load_fat_sectors
   729                              <1> 
   730                              <1> loc_update_fat16_cell:
   731                              <1> loc_update_fat16_buffer:
   732 0000C7CC 81C3001C0900        <1> 	add	ebx, FAT_Buffer ; 26/02/2016
   733                              <1> 	;movzx	eax, word [ebx]
   734 0000C7D2 668B03              <1> 	mov	ax, [ebx]
   735                              <1> 	; 01/03/2016
   736 0000C7D5 89C2                <1> 	mov	edx, eax ; old value of the cluster
   737 0000C7D7 A3[56660100]        <1> 	mov	[FAT_CurrentCluster], eax
   738 0000C7DC 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue] ; 32 bits
   739 0000C7E2 66890B              <1> 	mov	[ebx], cx ; 16 bits !
   740                              <1> 
   741 0000C7E5 C605[5A660100]02    <1> 	mov	byte [FAT_BuffValidData], 2
   742                              <1> 	
   743 0000C7EC 6683F802            <1> 	cmp	ax, 2
   744 0000C7F0 723A                <1> 	jb	short return_uc_fat_stc
   745 0000C7F2 3B05[66660100]      <1> 	cmp	eax, [LastCluster]
   746 0000C7F8 7732                <1> 	ja	short return_uc_fat_stc
   747                              <1> 
   748                              <1> loc_fat_buffer_updated:
   749                              <1> 	; 01/03/2016
   750 0000C7FA F8                  <1> 	clc
   751                              <1> loc_fat_buffer_stc_1:
   752 0000C7FB 9C                  <1> 	pushf
   753 0000C7FC 21C9                <1> 	and	ecx, ecx
   754 0000C7FE 7506                <1> 	jnz	short loc_fat_buffer_updated_1
   755                              <1> 
   756                              <1> 	; 01/03/2016 
   757                              <1> 	; new value of the cluster = 0 (free)
   758                              <1> 	; increase free(d) cluster count
   759 0000C800 FF05[62660100]      <1> 	inc	dword [FAT_ClusterCounter]
   760                              <1> 
   761                              <1> loc_fat_buffer_updated_1: ; new value of the cluster > 0
   762 0000C806 09D2                <1> 	or	edx, edx ; 02/03/2016
   763 0000C808 7506                <1> 	jnz	short loc_fat_buffer_updated_2
   764                              <1> 	; old value of the cluster = 0 (it was free cluster)
   765                              <1> 	; decrease free(d) cluster count
   766 0000C80A FF0D[62660100]      <1> 	dec	dword [FAT_ClusterCounter] ; it may be negative number
   767                              <1> 
   768                              <1> loc_fat_buffer_updated_2:
   769 0000C810 9D                  <1> 	popf
   770 0000C811 C3                  <1> 	retn
   771                              <1> 
   772                              <1> loc_uc_save_fat_buffer:
   773                              <1> 	; byte [FAT_BuffValidData] = 2 
   774 0000C812 E8D4010000          <1> 	call	save_fat_buffer
   775 0000C817 0F8297010000        <1>         jc      loc_fat_sectors_rw_error2
   776                              <1> 	;mov	byte [FAT_BuffValidData], 1
   777 0000C81D A1[56660100]        <1> 	mov	eax, [FAT_CurrentCluster]
   778                              <1> 	;mov	ecx, [ClusterValue]
   779                              <1> 	;jmp	short loc_update_cluster_check_fat_buffer
   780 0000C822 8A1E                <1> 	mov	bl, [esi+LD_Name] ; 01/03/2016
   781 0000C824 E927FFFFFF          <1>         jmp     loc_uc_reset_fat_buffer_validation
   782                              <1> 
   783                              <1> update_cluster_inv_data:
   784                              <1> 	;mov	eax, 0Dh
   785 0000C829 B00D                <1> 	mov	al, 0Dh  ; Invalid Data
   786 0000C82B C3                  <1> 	retn 
   787                              <1> 
   788                              <1> return_uc_fat_stc:
   789                              <1> 	; 01/03/2016
   790 0000C82C 31C0                <1> 	xor	eax, eax
   791 0000C82E F9                  <1> 	stc
   792 0000C82F EBCA                <1> 	jmp	short loc_fat_buffer_stc_1
   793                              <1> 
   794                              <1> update_fat12_cluster:
   795                              <1> pass_uc_fat12_errc:
   796                              <1> 	;sub	edx, edx
   797 0000C831 BB00040000          <1> 	mov	ebx, 400h ;1024
   798 0000C836 F7F3                <1> 	div	ebx
   799                              <1> 	; EAX = Count of 3 FAT sectors
   800                              <1> 	; DX = Cluster offset in FAT buffer
   801 0000C838 66B90300            <1> 	mov	cx, 3
   802 0000C83C 6689C3              <1> 	mov	bx, ax
   803 0000C83F 6689C8              <1> 	mov	ax, cx ; 3
   804 0000C842 66F7E2              <1> 	mul	dx     ; Multiply by 3
   805 0000C845 66D1E8              <1> 	shr	ax, 1  ; Divide by 2
   806 0000C848 6693                <1> 	xchg	bx, ax
   807                              <1> 	; EAX = Count of 3 FAT sectors
   808                              <1> 	; EBX = Byte Offset in FAT buffer   
   809 0000C84A 66F7E1              <1> 	mul	cx  ; 3 * AX
   810                              <1> 	; EAX = FAT Beginning Sector
   811                              <1> 	; EDX = 0
   812 0000C84D 8A0D[5A660100]      <1> 	mov	cl, [FAT_BuffValidData]
   813                              <1> 	; TRDOS v1 has a FATal bug here ! 
   814                              <1> 	; (it does not have 'cmp cl, 2' instruction here !
   815                              <1> 	;  while 'jne' is existing !)
   816 0000C853 80F902              <1> 	cmp	cl, 2 ; 2 = dirty buffer (must be written to disk)
   817 0000C856 750A                <1> 	jne	short loc_uc_check_fat12_buff_sector_load
   818                              <1> 
   819                              <1> loc_uc_check_fat12_buff_sector_save:
   820 0000C858 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   821 0000C85E 75B2                <1>         jne     short loc_uc_save_fat_buffer
   822 0000C860 EB15                <1> 	jmp	short loc_update_fat12_cell
   823                              <1> 
   824                              <1> loc_uc_check_fat12_buff_sector_load:
   825 0000C862 80F901              <1> 	cmp	cl, 1 ; byte ptr [FAT_BuffValidData]
   826 0000C865 0F8550010000        <1>         jne     loc_uc_load_fat_sectors
   827 0000C86B 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   828 0000C871 0F8544010000        <1>         jne     loc_uc_load_fat_sectors
   829                              <1> 
   830                              <1> loc_update_fat12_cell:
   831 0000C877 81C3001C0900        <1> 	add	ebx, FAT_Buffer ; 26/02/2016
   832 0000C87D 668B0D[56660100]    <1> 	mov	cx, [FAT_CurrentCluster]
   833 0000C884 66D1E9              <1> 	shr	cx, 1
   834 0000C887 668B03              <1> 	mov	ax, [ebx]
   835 0000C88A 6689C2              <1> 	mov	dx, ax
   836 0000C88D 7344                <1> 	jnc	short uc_fat12_nc_even
   837                              <1> 
   838 0000C88F 6683E00F            <1> 	and	ax, 0Fh
   839 0000C893 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue] ; 32 bits
   840 0000C899 66C1E104            <1> 	shl	cx, 4
   841 0000C89D 6609C1              <1> 	or	cx, ax
   842 0000C8A0 6689D0              <1> 	mov	ax, dx
   843 0000C8A3 66890B              <1> 	mov	[ebx], cx  ; 16 bits !
   844 0000C8A6 66C1E804            <1> 	shr	ax, 4 ; al(bit4..7)+ah(bit0..7)
   845                              <1> 
   846                              <1> update_fat12_buffer:
   847 0000C8AA A3[56660100]        <1> 	mov	[FAT_CurrentCluster], eax
   848 0000C8AF 89C2                <1> 	mov	edx, eax ; 01/03/2016
   849 0000C8B1 C605[5A660100]02    <1> 	mov	byte [FAT_BuffValidData], 2
   850 0000C8B8 6683F802            <1> 	cmp	ax, 2
   851 0000C8BC 0F826AFFFFFF        <1>         jb      return_uc_fat_stc
   852 0000C8C2 3B05[66660100]      <1> 	cmp	eax, [LastCluster]
   853 0000C8C8 0F875EFFFFFF        <1>         ja      return_uc_fat_stc
   854 0000C8CE E927FFFFFF          <1>         jmp     loc_fat_buffer_updated
   855                              <1> 
   856                              <1> uc_fat12_nc_even:
   857 0000C8D3 662500F0            <1> 	and	ax, 0F000h
   858 0000C8D7 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue] ; 32 bits
   859 0000C8DD 80E50F              <1> 	and	ch, 0Fh
   860 0000C8E0 6609C1              <1> 	or	cx, ax
   861 0000C8E3 6689D0              <1> 	mov	ax, dx
   862 0000C8E6 66890B              <1> 	mov	[ebx], cx ; 16 bits !
   863 0000C8E9 80E40F              <1> 	and	ah, 0Fh ; al(bit0..7)+ah(bit0..3)
   864 0000C8EC EBBC                <1> 	jmp	short update_fat12_buffer
   865                              <1> 
   866                              <1> update_fat32_cluster:
   867 0000C8EE 8B4E78              <1> 	mov	ecx, [esi+LD_Clusters]
   868 0000C8F1 41                  <1> 	inc	ecx
   869 0000C8F2 890D[66660100]      <1> 	mov	[LastCluster], ecx
   870                              <1> 
   871 0000C8F8 39C8                <1> 	cmp	eax, ecx
   872 0000C8FA 0F872CFFFFFF        <1>         ja      return_uc_fat_stc
   873                              <1> 
   874                              <1> pass_uc_fat32_errc:
   875                              <1> 	;sub	edx, edx
   876 0000C900 BB80010000          <1> 	mov	ebx, 180h ;384
   877 0000C905 F7F3                <1> 	div	ebx
   878                              <1> 	; EAX = Count of 3 FAT sectors
   879                              <1> 	; DX = Cluster offset in FAT buffer
   880 0000C907 89D3                <1> 	mov	ebx, edx
   881 0000C909 C1E302              <1> 	shl	ebx, 2 ; Multiply by 4
   882 0000C90C BA03000000          <1> 	mov	edx, 3	
   883 0000C911 F7E2                <1> 	mul	edx
   884                              <1> 	; EBX = Cluster Offset in FAT buffer
   885                              <1> 	; EAX = FAT Sector
   886                              <1> 	; EDX = 0
   887 0000C913 8A0D[5A660100]      <1> 	mov	cl, [FAT_BuffValidData]
   888 0000C919 80F902              <1> 	cmp	cl, 2
   889 0000C91C 750E                <1> 	jne	short loc_uc_check_fat32_buff_sector_load
   890                              <1> 
   891                              <1> loc_uc_check_fat32_buff_sector_save:
   892 0000C91E 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   893 0000C924 0F85E8FEFFFF        <1>         jne     loc_uc_save_fat_buffer
   894 0000C92A EB11                <1> 	jmp	short loc_update_fat32_cell
   895                              <1> 
   896                              <1> loc_uc_check_fat32_buff_sector_load:
   897 0000C92C 80F901              <1> 	cmp	cl, 1 ; byte [FAT_BuffValidData]
   898 0000C92F 0F8586000000        <1>         jne     loc_uc_load_fat_sectors
   899 0000C935 3B05[5E660100]      <1> 	cmp	eax, [FAT_BuffSector]
   900 0000C93B 757E                <1>         jne     loc_uc_load_fat_sectors
   901                              <1> 
   902                              <1> loc_update_fat32_cell:
   903                              <1> loc_update_fat32_buffer:
   904 0000C93D 81C3001C0900        <1> 	add	ebx, FAT_Buffer ; 26/02/2016
   905 0000C943 8B03                <1> 	mov	eax, [ebx]
   906 0000C945 25FFFFFF0F          <1> 	and	eax, 0FFFFFFFh ; 28 bit cluster value
   907                              <1> 	
   908 0000C94A 8B15[56660100]      <1> 	mov	edx, [FAT_CurrentCluster] ; 01/03/2016
   909                              <1> 
   910 0000C950 A3[56660100]        <1> 	mov 	[FAT_CurrentCluster], eax
   911 0000C955 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue]
   912 0000C95B 890B                <1> 	mov	[ebx], ecx ; 29/02/2016 
   913                              <1> 
   914 0000C95D C605[5A660100]02    <1> 	mov	byte [FAT_BuffValidData], 2
   915                              <1> 
   916                              <1> 	; 01/03/2016
   917 0000C964 21C0                <1> 	and	eax, eax ; was it free cluster ?
   918 0000C966 7514                <1> 	jnz	short loc_upd_fat32_c0
   919                              <1> 
   920                              <1> 	;or	ecx, ecx ; it will be left free ?!
   921                              <1> 	;jz	short loc_upd_fat32_c3
   922                              <1> 
   923 0000C968 3B563E              <1> 	cmp	edx, [esi+LD_BPB+BPB_Reserved+4] ; First free cluster
   924 0000C96B 7520                <1> 	jne	short loc_upd_fat32_c3
   925                              <1> 
   926 0000C96D 3B15[66660100]      <1> 	cmp	edx, [LastCluster]
   927 0000C973 7207                <1> 	jb	short loc_upd_fat32_c0
   928                              <1> 
   929 0000C975 BA02000000          <1> 	mov	edx, 2 ; rewind !
   930 0000C97A EB0E                <1> 	jmp	short loc_upd_fat32_c2
   931                              <1> 
   932                              <1> loc_upd_fat32_c0:
   933 0000C97C FF463E              <1> 	inc	dword [esi+LD_BPB+BPB_Reserved+4] ; set it to next cluster		
   934 0000C97F EB0C                <1> 	jmp	short loc_upd_fat32_c3
   935                              <1> 
   936                              <1> loc_upd_fat32_c1:
   937 0000C981 09C9                <1> 	or	ecx, ecx ; will it be free cluster ?
   938 0000C983 7508                <1> 	jnz	short loc_upd_fat32_c3
   939                              <1> 
   940 0000C985 3B563E              <1> 	cmp	edx, [esi+LD_BPB+BPB_Reserved+4] ; First free cluster
   941 0000C988 7303                <1> 	jnb	short loc_upd_fat32_c3
   942                              <1> 
   943                              <1> loc_upd_fat32_c2:	
   944 0000C98A 89563E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], edx			
   945                              <1> 
   946                              <1> loc_upd_fat32_c3:
   947 0000C98D 89C2                <1> 	mov	edx, eax
   948                              <1> 
   949                              <1> loc_upd_fat32_c4:
   950 0000C98F 83F802              <1> 	cmp	eax, 2
   951 0000C992 0F8294FEFFFF        <1>         jb      return_uc_fat_stc
   952                              <1> 
   953                              <1> pass_uc_fat32_c_zero_check_2:
   954 0000C998 3B05[66660100]      <1> 	cmp	eax, [LastCluster]
   955 0000C99E 0F8788FEFFFF        <1>         ja      return_uc_fat_stc
   956                              <1> 	
   957 0000C9A4 E951FEFFFF          <1> 	jmp     loc_fat_buffer_updated
   958                              <1> 
   959                              <1> loc_fat_sectors_rw_error1:
   960                              <1> 	;mov	byte [FAT_BuffValidData], 0
   961                              <1> 	; 23/10/2016 (15h -> 17)
   962                              <1> 	; 23/03/2016
   963 0000C9A9 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error
   964 0000C9AE 8825[5A660100]      <1> 	mov	[FAT_BuffValidData], ah ; 0
   965                              <1> 
   966                              <1> loc_fat_sectors_rw_error2:
   967                              <1> 	;mov	eax, error code
   968                              <1> 	;mov	edx, 0
   969 0000C9B4 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue]
   970 0000C9BA C3                  <1> 	retn
   971                              <1> 
   972                              <1> loc_uc_load_fat_sectors:
   973 0000C9BB A3[5E660100]        <1> 	mov	[FAT_BuffSector], eax
   974                              <1> 
   975                              <1> load_uc_fat_sectors_zero:
   976 0000C9C0 034660              <1> 	add	eax, [esi+LD_FATBegin]
   977 0000C9C3 BB001C0900          <1> 	mov	ebx, FAT_Buffer
   978 0000C9C8 B903000000          <1> 	mov	ecx, 3
   979 0000C9CD E8EF330000          <1> 	call	disk_read
   980 0000C9D2 72D5                <1> 	jc	short loc_fat_sectors_rw_error1
   981                              <1> 
   982 0000C9D4 C605[5A660100]01    <1>         mov     byte [FAT_BuffValidData], 1
   983 0000C9DB A1[56660100]        <1> 	mov 	eax, [FAT_CurrentCluster]
   984 0000C9E0 8B0D[F8680100]      <1> 	mov	ecx, [ClusterValue]
   985 0000C9E6 E972FDFFFF          <1>         jmp     loc_update_cluster_check_fat_type
   986                              <1> 
   987                              <1> save_fat_buffer:
   988                              <1> 	; 15/10/2016
   989                              <1> 	; 01/03/2016
   990                              <1> 	; 22/02/2016 (TRDOS 386 =  TRDOS v2.0)
   991                              <1> 	; 11/08/2011
   992                              <1> 	; 09/02/2005 
   993                              <1> 	; INPUT ->
   994                              <1> 	;	None
   995                              <1> 	; OUTPUT ->
   996                              <1> 	;	cf = 0 -> OK.
   997                              <1> 	;	cf = 1 -> error code in AL (EAX)
   998                              <1> 	;
   999                              <1> 	;	EBX = FAT_Buffer address
  1000                              <1> 	;
  1001                              <1> 	; (EAX, EDX, ECX will be modified)
  1002                              <1> 
  1003                              <1> 	;cmp	byte [FAT_BuffValidData], 2 
  1004                              <1> 	;je	short loc_save_fat_buff
  1005                              <1> 
  1006                              <1> ;loc_save_fat_buffer_retn:
  1007                              <1> ;	xor	eax, eax
  1008                              <1> ;	retn
  1009                              <1> 
  1010                              <1> loc_save_fat_buff:
  1011 0000C9EB 31D2                <1> 	xor	edx, edx
  1012 0000C9ED 8A35[5B660100]      <1> 	mov	dh, [FAT_BuffDrvName]
  1013 0000C9F3 80FE41              <1> 	cmp	dh, 'A'
  1014 0000C9F6 722E                <1> 	jb	short loc_save_fat_buffer_inv_data_retn
  1015 0000C9F8 80EE41              <1> 	sub	dh, 'A'
  1016 0000C9FB 56                  <1> 	push	esi ; *
  1017 0000C9FC BE00010900          <1>         mov     esi, Logical_DOSDisks
  1018 0000CA01 01D6                <1> 	add	esi, edx
  1019                              <1> 	
  1020 0000CA03 8A5603              <1> 	mov	dl, [esi+LD_FATType]
  1021 0000CA06 20D2                <1> 	and	dl, dl
  1022 0000CA08 741B                <1> 	jz	short loc_save_fat_buffer_inv_data_pop_retn 
  1023                              <1> 
  1024 0000CA0A A1[5E660100]        <1> 	mov	eax, [FAT_BuffSector]
  1025 0000CA0F 80FA02              <1> 	cmp	dl, 2
  1026 0000CA12 770A                <1> 	ja	short loc_save_fat32_buff
  1027                              <1> 
  1028                              <1> loc_save_fat_12_16_buff:
  1029                              <1> 	; 01/03/2016
  1030                              <1> 	; TRDOS v1 has a FATal bug here!
  1031                              <1> 	; Correct code: mov dx, word ptr [FAT_BuffSector]+2
  1032                              <1> 	; (DX:AX in TRDOS v1 -> EAX in TRDOS v2)
  1033                              <1> 	;
  1034 0000CA14 0FB74E1C            <1> 	movzx	ecx, word [esi+LD_BPB+FATSecs] 
  1035 0000CA18 29C1                <1> 	sub	ecx, eax
  1036                              <1> 	; TRDOS v1 has a bug here... ('pop esi' was forgotten!)
  1037                              <1> 	;jna	short loc_save_fat_buffer_inv_data_retn ; wrong addr!
  1038 0000CA1A 7609                <1> 	jna	short loc_save_fat_buffer_inv_data_pop_retn ; correct addr.
  1039 0000CA1C EB15                <1> 	jmp	short loc_save_fat_buffer_check_rs3
  1040                              <1> 
  1041                              <1> loc_save_fat32_buff:
  1042 0000CA1E 8B4E2A              <1> 	mov	ecx, [esi+LD_BPB+FAT32_FAT_Size]
  1043 0000CA21 29C1                <1> 	sub	ecx, eax
  1044 0000CA23 770E                <1> 	ja	short loc_save_fat_buffer_check_rs3
  1045                              <1> 
  1046                              <1> loc_save_fat_buffer_inv_data_pop_retn:
  1047 0000CA25 5E                  <1> 	pop	esi ; *
  1048                              <1> loc_save_fat_buffer_inv_data_retn:
  1049 0000CA26 B80D000000          <1> 	mov	eax, 0Dh ; Invalid DATA
  1050 0000CA2B C3                  <1> 	retn
  1051                              <1> 
  1052                              <1> loc_save_fat_buff_remain_sectors_3:
  1053 0000CA2C B903000000          <1> 	mov	ecx, 3
  1054 0000CA31 EB05                <1> 	jmp	short loc_save_fat_buff_continue
  1055                              <1> 
  1056                              <1> loc_save_fat_buffer_check_rs3:
  1057 0000CA33 83F903              <1> 	cmp	ecx, 3
  1058 0000CA36 77F4                <1> 	ja	short loc_save_fat_buff_remain_sectors_3
  1059                              <1> 
  1060                              <1> loc_save_fat_buff_continue:
  1061 0000CA38 BB001C0900          <1> 	mov	ebx, FAT_Buffer
  1062 0000CA3D 034660              <1> 	add	eax, [esi+LD_FATBegin]
  1063 0000CA40 51                  <1> 	push	ecx
  1064 0000CA41 E86C330000          <1> 	call	disk_write
  1065 0000CA46 59                  <1> 	pop	ecx
  1066 0000CA47 722B                <1> 	jc	short loc_save_FAT_buff_write_err
  1067                              <1> 	
  1068 0000CA49 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
  1069 0000CA4D 7605                <1> 	jna	short loc_calc_2nd_fat12_16_addr
  1070                              <1> 
  1071                              <1> loc_calc_2nd_fat32_addr:
  1072 0000CA4F 8B462A              <1> 	mov	eax, [esi+LD_BPB+FAT32_FAT_Size]
  1073 0000CA52 EB04                <1> 	jmp	short loc_calc_2nd_fat_addr
  1074                              <1> 
  1075                              <1> loc_calc_2nd_fat12_16_addr:
  1076 0000CA54 0FB7461C            <1> 	movzx	eax, word [esi+LD_BPB+FATSecs]
  1077                              <1> 
  1078                              <1> loc_calc_2nd_fat_addr:
  1079 0000CA58 034660              <1> 	add	eax, [esi+LD_FATBegin]
  1080 0000CA5B 0305[5E660100]      <1> 	add	eax, [FAT_BuffSector]
  1081 0000CA61 BB001C0900          <1> 	mov	ebx, FAT_Buffer
  1082                              <1> 	; ecx = 1 to 3
  1083 0000CA66 E847330000          <1> 	call	disk_write
  1084 0000CA6B 7207                <1> 	jc	short loc_save_FAT_buff_write_err
  1085                              <1>  	; Valid  buffer (1 = valid but do not save)
  1086 0000CA6D C605[5A660100]01    <1> 	mov	byte [FAT_BuffValidData], 1
  1087                              <1> 
  1088                              <1> loc_save_FAT_buff_write_err:
  1089 0000CA74 5E                  <1> 	pop	esi ; *
  1090 0000CA75 BB001C0900          <1> 	mov	ebx, FAT_Buffer
  1091                              <1> 	; 15/10/2016 (1Dh -> 18)
  1092                              <1> 	; 23/03/2016 (1Dh)
  1093 0000CA7A B812000000          <1> 	mov	eax, 18 ; Drive not ready or write error
  1094 0000CA7F C3                  <1> 	retn
  1095                              <1> 
  1096                              <1> calculate_fat_freespace:
  1097                              <1> 	; 23/03/2016
  1098                              <1> 	; 02/03/2016
  1099                              <1> 	; 01/03/2016
  1100                              <1> 	; 29/02/2016
  1101                              <1> 	; 22/02/2016 (TRDOS 386 =  TRDOS v2.0)
  1102                              <1> 	; 30/04/2011
  1103                              <1> 	; 03/04/2010
  1104                              <1> 	; 2005
  1105                              <1> 	; INPUT ->
  1106                              <1> 	;	EAX = Cluster count to be added or subtracted
  1107                              <1> 	; 	If BH = FFh, ESI = TR-DOS Logical Drive Description Table
  1108                              <1> 	; 	If BH < FFh, BH = TR-DOS Logical Drive Number
  1109                              <1> 	; 	BL: 
  1110                              <1> 	;	0 = Calculate, 1 = Add, 2 = Subtract, 3 = Get (Not Set/Calc)
  1111                              <1> 	; OUTPUT ->
  1112                              <1> 	;	EAX = Free Space in sectors
  1113                              <1> 	;	ESI = Logical Dos Drive Description Table address
  1114                              <1> 	;	BH = Logical Dos Drive Number (same with input value of BH)
  1115                              <1> 	;	BL = Type of operation (same with input value of BL)
  1116                              <1> 	;	ECX = 0 -> valid
  1117                              <1> 	;	ECX > 0 -> error or invalid
  1118                              <1> 	;	If EAX = FFFFFFFFh, it is 're-calculation needed'
  1119                              <1> 	;			          sign due to r/w error   
  1120                              <1> 
  1121 0000CA80 66891D[FE680100]    <1> 	mov	[CFS_OPType], bx
  1122 0000CA87 A3[00690100]        <1> 	mov	[CFS_CC], eax
  1123                              <1> 	
  1124 0000CA8C 80FFFF              <1> 	cmp	bh, 0FFh
  1125 0000CA8F 740B                <1> 	je	short pass_calculate_freespace_get_drive_dt_offset
  1126                              <1> 
  1127                              <1> loc_calculate_freespace_get_drive_dt_offset:     
  1128 0000CA91 31C0                <1> 	xor	eax, eax
  1129 0000CA93 88FC                <1>         mov     ah, bh
  1130 0000CA95 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  1131 0000CA9A 01C6                <1>         add     esi, eax
  1132                              <1> 
  1133                              <1> pass_calculate_freespace_get_drive_dt_offset:
  1134 0000CA9C 08DB                <1> 	or	bl, bl
  1135 0000CA9E 7435                <1> 	jz	short loc_reset_fcc
  1136                              <1> 	
  1137                              <1> loc_get_free_sectors:
  1138 0000CAA0 8B4674              <1> 	mov	eax, [esi+LD_FreeSectors]
  1139                              <1> 
  1140                              <1> 	;xor	ecx, ecx
  1141                              <1> 	;dec	ecx ; 0FFFFFFFFh
  1142                              <1> 	;cmp	eax, ecx ; 29/02/2016
  1143                              <1> 	;je	short loc_get_free_sectors_retn ; recalculation is needed!
  1144                              <1> 	
  1145                              <1> 	; 23/03/2016
  1146 0000CAA3 8B4E70              <1> 	mov	ecx, [esi+LD_TotalSectors]
  1147 0000CAA6 39C1                <1> 	cmp	ecx, eax ; Total sectors must be greater than Free sectors !
  1148 0000CAA8 7707                <1> 	ja	short loc_get_free_sectors_check_optype
  1149                              <1> 	
  1150 0000CAAA 31C0                <1> 	xor	eax, eax
  1151 0000CAAC 48                  <1> 	dec	eax ; 0FFFFFFFFh  ; recalculation is needed!
  1152 0000CAAD 894674              <1> 	mov	[esi+LD_FreeSectors], eax ; reset (for recalculation)
  1153                              <1> 		
  1154                              <1> loc_get_free_sectors_retn:
  1155 0000CAB0 C3                  <1> 	retn
  1156                              <1> 	
  1157                              <1> loc_get_free_sectors_check_optype:
  1158 0000CAB1 80FB03              <1> 	cmp	bl, 3
  1159 0000CAB4 7203                <1> 	jb	short loc_set_fcc
  1160                              <1> 
  1161 0000CAB6 29C9                <1> 	sub	ecx, ecx ; 0
  1162                              <1> 
  1163 0000CAB8 C3                  <1> 	retn	
  1164                              <1> 
  1165                              <1> loc_set_fcc:
  1166 0000CAB9 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
  1167 0000CABD 0F87DF000000        <1>         ja      loc_update_FAT32_fs_info_fcc
  1168                              <1> 
  1169                              <1> 	;mov	eax, [esi+LD_FreeSectors]
  1170 0000CAC3 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+SecPerClust]
  1171 0000CAC7 29D2                <1> 	sub	edx, edx
  1172 0000CAC9 F7F1                <1> 	div	ecx
  1173                              <1> 	;or	dx, dx 
  1174                              <1> 	;	; DX -> Remain sectors < SecPerClust
  1175                              <1> 	;	; DX > 0 -> invalid free sector count
  1176                              <1> 	;jnz	short loc_reset_fcc 
  1177                              <1> 
  1178                              <1> ;pass_set_fcc_div32:
  1179 0000CACB A3[77660100]        <1> 	mov	[FreeClusterCount], eax
  1180 0000CAD0 E988000000          <1>         jmp     loc_set_free_sectors_FAT12_FAT16
  1181                              <1> 
  1182                              <1> loc_reset_fcc:
  1183 0000CAD5 31C0                <1> 	xor	eax, eax
  1184 0000CAD7 A3[77660100]        <1> 	mov	[FreeClusterCount], eax ; 0
  1185 0000CADC 8B5678              <1> 	mov	edx, [esi+LD_Clusters]
  1186 0000CADF 42                  <1> 	inc	edx
  1187 0000CAE0 8915[66660100]      <1> 	mov	[LastCluster], edx
  1188                              <1> 
  1189 0000CAE6 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
  1190 0000CAEA 7647                <1> 	jna	short loc_count_free_fat_clusters_0  
  1191                              <1> 
  1192 0000CAEC 48                  <1> 	dec	eax ; FFFFFFFFh
  1193 0000CAED A3[08690100]        <1> 	mov	[CFS_FAT32FC], eax
  1194                              <1> 
  1195                              <1> 	; 29/02/2016
  1196 0000CAF2 89463A              <1> 	mov	[esi+LD_BPB+BPB_Reserved], eax ; reset
  1197 0000CAF5 89463E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], eax ; reset
  1198                              <1> 	
  1199 0000CAF8 B802000000          <1> 	mov 	eax, 2
  1200                              <1> 
  1201                              <1> loc_count_fc_next_cluster_0:
  1202 0000CAFD 50                  <1> 	push	eax
  1203 0000CAFE E801F9FFFF          <1> 	call	get_next_cluster
  1204 0000CB03 7310                <1> 	jnc	short loc_check_fat32_ff_cluster
  1205 0000CB05 09C0                <1> 	or	eax, eax
  1206 0000CB07 741E                <1> 	jz	short pass_inc_cfs_fcc_0
  1207                              <1> 
  1208                              <1> loc_put_fcc_unknown_sign:
  1209 0000CB09 58                  <1> 	pop	eax
  1210                              <1> 	; "Free count is Unknown" sign
  1211                              <1> 	;mov	dword [FreeClusterCount], 0FFFFFFFFh
  1212                              <1> 
  1213                              <1> 	; 29/02/2016
  1214                              <1> 	; Save Free Cluster Count value in FAT32 'BPB_Reserved' area
  1215                              <1> 	;mov	[esi+LD_BPB+BPB_Reserved], 0FFFFFFFFh ; unknown!
  1216 0000CB0A 8B15[08690100]      <1> 	mov	edx, [CFS_FAT32FC] ; First Free Cluster
  1217                              <1> 	; Save First Free Cluster value in FAT32 'BPB_Reserved+4' area
  1218 0000CB10 89563E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], edx
  1219                              <1> 	
  1220 0000CB13 EB7D                <1>         jmp     loc_put_fcc_invalid_sign
  1221                              <1> 
  1222                              <1> loc_check_fat32_ff_cluster:
  1223 0000CB15 09C0                <1> 	or	eax, eax
  1224 0000CB17 750E                <1> 	jnz	short pass_inc_cfs_fcc_0
  1225 0000CB19 58                  <1> 	pop	eax
  1226 0000CB1A A3[08690100]        <1> 	mov	[CFS_FAT32FC], eax
  1227                              <1> 	;mov	dword [FreeClusterCount], 1
  1228 0000CB1F FF05[77660100]      <1> 	inc	dword [FreeClusterCount]
  1229 0000CB25 EB27                <1> 	jmp	short pass_inc_cfs_fcc_1
  1230                              <1> 
  1231                              <1> pass_inc_cfs_fcc_0:
  1232 0000CB27 58                  <1> 	pop	eax
  1233                              <1> 
  1234                              <1> pass_inc_cfs_fcc_0c:
  1235 0000CB28 40                  <1> 	inc	eax ; add eax, 1
  1236 0000CB29 3B05[66660100]      <1> 	cmp	eax, [LastCluster]
  1237 0000CB2F 76CC                <1> 	jna 	short loc_count_fc_next_cluster_0
  1238 0000CB31 EB6F                <1> 	jmp	short loc_update_FAT32_fs_info_fcc
  1239                              <1> 
  1240                              <1> loc_count_free_fat_clusters_0:
  1241                              <1> 	;mov	eax, 2
  1242 0000CB33 B002                <1> 	mov	al, 2
  1243                              <1> 
  1244                              <1> loc_count_fc_next_cluster:
  1245 0000CB35 50                  <1> 	push	eax
  1246 0000CB36 E8C9F8FFFF          <1> 	call	get_next_cluster
  1247 0000CB3B 720C                <1> 	jc	short loc_count_fcc_stc
  1248                              <1> 
  1249                              <1> loc_count_free_clusters_1:
  1250 0000CB3D 21C0                <1> 	and	eax, eax
  1251 0000CB3F 750C                <1> 	jnz	short pass_inc_cfs_fcc
  1252                              <1> 
  1253 0000CB41 FF05[77660100]      <1> 	inc	dword [FreeClusterCount]
  1254 0000CB47 EB04                <1> 	jmp	short pass_inc_cfs_fcc
  1255                              <1> 
  1256                              <1> loc_count_fcc_stc:
  1257 0000CB49 09C0                <1> 	or	eax, eax
  1258 0000CB4B 75BC                <1> 	jnz	short loc_put_fcc_unknown_sign ; 29/02/2016
  1259                              <1> 
  1260                              <1> pass_inc_cfs_fcc:
  1261 0000CB4D 58                  <1> 	pop	eax
  1262                              <1> 
  1263                              <1> pass_inc_cfs_fcc_1:
  1264 0000CB4E 40                  <1> 	inc	eax ; add eax, 1
  1265 0000CB4F 3B05[66660100]      <1> 	cmp	eax, [LastCluster]
  1266 0000CB55 76DE                <1> 	jna	short loc_count_fc_next_cluster
  1267                              <1> 
  1268                              <1> loc_set_free_sectors:
  1269 0000CB57 807E0302            <1> 	cmp	byte [esi+LD_FATType], 2
  1270 0000CB5B 7745                <1> 	ja	short loc_update_FAT32_fs_info_fcc
  1271                              <1> 
  1272                              <1> loc_set_free_sectors_FAT12_FAT16:
  1273 0000CB5D 803D[FE680100]00    <1> 	cmp	byte [CFS_OPType], 0
  1274 0000CB64 761C                <1> 	jna	short pass_FAT_add_sub_fcc
  1275 0000CB66 A1[00690100]        <1> 	mov	eax, [CFS_CC]
  1276 0000CB6B 803D[FE680100]01    <1> 	cmp	byte [CFS_OPType], 1
  1277 0000CB72 7708                <1> 	ja	short pass_FAT_add_fcc
  1278 0000CB74 0105[77660100]      <1> 	add 	[FreeClusterCount], eax
  1279 0000CB7A EB06                <1> 	jmp	short pass_FAT_add_sub_fcc
  1280                              <1> 
  1281                              <1> pass_FAT_add_fcc:
  1282 0000CB7C 2905[77660100]      <1> 	sub	[FreeClusterCount], eax
  1283                              <1> 
  1284                              <1> pass_FAT_add_sub_fcc:
  1285 0000CB82 0FB64613            <1> 	movzx	eax, byte [esi+LD_BPB+SecPerClust]
  1286 0000CB86 8B15[77660100]      <1> 	mov	edx, [FreeClusterCount]
  1287 0000CB8C F7E2                <1> 	mul	edx
  1288                              <1> 
  1289 0000CB8E 31C9                <1> 	xor	ecx, ecx 
  1290 0000CB90 EB05                <1> 	jmp	short loc_cfs_retn_params
  1291                              <1> 
  1292                              <1> loc_put_fcc_invalid_sign:
  1293 0000CB92 29C0                <1>        	sub	eax, eax ; 0
  1294 0000CB94 48                  <1> 	dec	eax ; FFFFFFFFh
  1295                              <1> loc_fat32_ffc_recalc_needed:
  1296 0000CB95 89C1                <1> 	mov	ecx, eax
  1297                              <1> 
  1298                              <1> loc_cfs_retn_params:
  1299 0000CB97 894674              <1> 	mov 	[esi+LD_FreeSectors], eax
  1300 0000CB9A 0FB71D[FE680100]    <1> 	movzx	ebx, word [CFS_OPType]
  1301 0000CBA1 C3                  <1> 	retn
  1302                              <1> 
  1303                              <1> loc_update_FAT32_fs_info_fcc:
  1304                              <1> loc_check_fcc_FSINFO_op:
  1305                              <1> 	; 29/02/2016
  1306                              <1> 	; EAX = Free cluster count (before this update) ; value from disk
  1307                              <1> 	; EDX = First Free Cluster (before this update) ; value from disk
  1308 0000CBA2 803D[FE680100]01    <1> 	cmp	byte [CFS_OPType], 1
  1309 0000CBA9 7221                <1> 	jb	short loc_cfs_FAT32_get_rcalc_parms ; 0 = recalculated
  1310 0000CBAB 7406                <1> 	je	short loc_check_fcc_FSINFO_op1 ; 1 = add
  1311                              <1> loc_check_fcc_FSINFO_op2: ; subtract
  1312 0000CBAD F71D[00690100]      <1> 	neg	dword [CFS_CC] ; prepare to subtract ; 2 = sub (add negative)
  1313                              <1> loc_check_fcc_FSINFO_op1:
  1314                              <1> 	; 01/03/2016
  1315 0000CBB3 31D2                <1> 	xor	edx, edx ; 0
  1316 0000CBB5 4A                  <1> 	dec	edx ; 0FFFFFFFFh
  1317 0000CBB6 8B463A              <1> 	mov	eax, [esi+LD_BPB+BPB_Reserved]
  1318 0000CBB9 39D0                <1> 	cmp	eax, edx
  1319 0000CBBB 73D5                <1> 	jnb	short loc_put_fcc_invalid_sign
  1320 0000CBBD 0305[00690100]      <1>         add     eax, [CFS_CC] ; free cluster count on disk + current count
  1321 0000CBC3 72CD                <1> 	jc	short loc_put_fcc_invalid_sign
  1322                              <1> 	
  1323 0000CBC5 A3[77660100]        <1> 	mov	[FreeClusterCount], eax
  1324 0000CBCA EB0E                <1> 	jmp	short loc_cfs_write_FSINFO_sector
  1325                              <1> 
  1326                              <1> loc_cfs_FAT32_get_rcalc_parms:
  1327 0000CBCC 8B15[08690100]      <1> 	mov	edx, [CFS_FAT32FC]
  1328 0000CBD2 A1[77660100]        <1> 	mov	eax, [FreeClusterCount]
  1329 0000CBD7 89563E              <1> 	mov	[esi+LD_BPB+BPB_Reserved+4], edx ; First Free Cluster
  1330                              <1> loc_cfs_write_FSINFO_sector:
  1331 0000CBDA 89463A              <1> 	mov	[esi+LD_BPB+BPB_Reserved], eax ; Free cluster count
  1332                              <1> 	; 01/03/2016
  1333 0000CBDD E8AA000000          <1> 	call	set_fat32_fsinfo_sector_parms
  1334 0000CBE2 72AE                <1>         jc      short loc_put_fcc_invalid_sign
  1335                              <1> 
  1336                              <1> loc_set_FAT32_free_sectors:
  1337                              <1> 	; 29/02/2016
  1338                              <1> 	;mov	eax, [FreeClusterCount]
  1339                              <1> 	;mov	ecx, eax
  1340                              <1> 	;cmp	eax, 0FFFFFFFFh ; Invalid !
  1341                              <1> 	;je	short loc_cfs_retn_params
  1342                              <1> 	;
  1343 0000CBE4 8B0D[77660100]      <1> 	mov	ecx, [FreeClusterCount]
  1344 0000CBEA 0FB64613            <1> 	movzx	eax, byte [esi+LD_BPB+SecPerClust]
  1345 0000CBEE F7E1                <1> 	mul	ecx
  1346                              <1> 	; 29/02/2016
  1347 0000CBF0 31C9                <1> 	xor	ecx, ecx ; 0
  1348 0000CBF2 09D2                <1> 	or	edx, edx ; 0 ?
  1349 0000CBF4 759C                <1>         jnz     loc_put_fcc_invalid_sign
  1350 0000CBF6 394670              <1> 	cmp	[esi+LD_TotalSectors], eax ; Volume size in sectors
  1351 0000CBF9 7697                <1>         jna     short loc_put_fcc_invalid_sign
  1352                              <1> 	;
  1353                              <1> loc_set_FAT32_free_sectors_ok:
  1354 0000CBFB 31D2                <1> 	xor	edx, edx ; 0
  1355 0000CBFD EB98                <1>         jmp     short loc_cfs_retn_params 
  1356                              <1> 	;
  1357                              <1> 
  1358                              <1> get_last_cluster:
  1359                              <1> 	; 22/10/2016
  1360                              <1> 	; 27/02/2016 (TRDOS 386 =  TRDOS v2.0)
  1361                              <1> 	; 12/06/2010 (DRV_FAT.ASM, 'proc_get_last_custer')
  1362                              <1> 	; 06/06/2010
  1363                              <1> 	; INPUT ->
  1364                              <1> 	;	EAX = First Cluster Number
  1365                              <1> 	; 	ESI = Logical Dos Drive Parameters Table
  1366                              <1> 	; OUTPUT ->
  1367                              <1> 	;	cf = 0 -> No Error, EAX is valid
  1368                              <1> 	;	cf = 1 -> EAX > 0 -> Error
  1369                              <1> 	;	EAX = Last Cluster Number
  1370                              <1> 	;       ECX = Previous Cluster -just before the last cluster-
  1371                              <1> 	;       ; 22/10/2016
  1372                              <1> 	;	[glc_index] = cluster index number of the last cluster	
  1373                              <1> 	;
  1374                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
  1375                              <1> 
  1376 0000CBFF 89C1                <1> 	mov	ecx, eax
  1377                              <1> 
  1378 0000CC01 C705[10690100]FFFF- <1> 	mov	dword [glc_index], 0FFFFFFFFh ; 22/10/2016	
  1378 0000CC09 FFFF                <1>
  1379                              <1> 
  1380                              <1> loc_glc_get_next_cluster_1:
  1381 0000CC0B 890D[0C690100]      <1> 	mov	[glc_prevcluster], ecx
  1382                              <1>  	; 22/10/2016
  1383 0000CC11 FF05[10690100]      <1> 	inc	dword [glc_index]
  1384                              <1> 
  1385                              <1> loc_glc_get_next_cluster_2:
  1386 0000CC17 E8E8F7FFFF          <1> 	call	get_next_cluster
  1387                              <1> 	; ecx = current/previous cluster 
  1388                              <1> 	; eax = next/last cluster
  1389 0000CC1C 73ED                <1> 	jnc	short loc_glc_get_next_cluster_1
  1390                              <1> 
  1391 0000CC1E 09C0                <1> 	or	eax, eax
  1392 0000CC20 7509                <1> 	jnz	short loc_glc_stc_retn
  1393                              <1> 
  1394                              <1> 	; ecx = previous cluster
  1395 0000CC22 89C8                <1>         mov	eax, ecx
  1396                              <1> 
  1397                              <1> 	; previous cluster becomes last cluster (ecx -> eax)
  1398                              <1> 	; previous of previous cluster becomes previous cluster (ecx)
  1399                              <1> 
  1400                              <1> loc_glc_prev_cluster_retn:
  1401 0000CC24 8B0D[0C690100]      <1> 	mov	ecx, [glc_prevcluster] 
  1402 0000CC2A C3                  <1> 	retn
  1403                              <1> 
  1404                              <1> loc_glc_stc_retn:
  1405 0000CC2B F5                  <1> 	cmc	;stc
  1406 0000CC2C EBF6                <1>         jmp	short loc_glc_prev_cluster_retn
  1407                              <1> 
  1408                              <1> truncate_cluster_chain:
  1409                              <1> 	; 01/03/2016
  1410                              <1> 	; 28/02/2016 (TRDOS 386 =  TRDOS v2.0)
  1411                              <1> 	; 22/01/2011 (DRV_FAT.ASM, 'proc_truncate_cluster_chain')
  1412                              <1> 	; 11/09/2010
  1413                              <1> 	; INPUT ->
  1414                              <1> 	;	ESI = Logical dos drive description table address
  1415                              <1> 	;	EAX = First cluster to be truncated/unlinked 
  1416                              <1> 	; OUTPUT ->
  1417                              <1> 	;	ESI = Logical dos drive description table address
  1418                              <1> 	; 	ECX = Count of truncated/removed clusters
  1419                              <1> 	; 	CF = 0 -> EAX = Free sectors
  1420                              <1> 	; 	CF = 1 -> Error code in EAX (AL)
  1421                              <1> 
  1422                              <1> 	; NOTE: This procedure does not update lm date&time ! 
  1423                              <1> 
  1424                              <1> loc_truncate_cc:	
  1425 0000CC2E 31C9                <1> 	xor	ecx, ecx ; mov ecx, 0
  1426                              <1> 	;mov	byte [FAT_BuffValidData], 0
  1427 0000CC30 890D[62660100]      <1> 	mov	[FAT_ClusterCounter], ecx ; 0 ; reset
  1428                              <1> 
  1429                              <1> loc_tcc_unlink_clusters:
  1430 0000CC36 E8F3FAFFFF          <1> 	call	update_cluster
  1431                              <1> 	; EAX = Next Cluster
  1432                              <1> 	; ECX = Cluster Value
  1433                              <1> 	; Note:
  1434                              <1> 	; Returns count of unlinked clusters in
  1435                              <1> 	; dword ptr FAT_ClusterCounter
  1436 0000CC3B 73F9                <1> 	jnc short loc_tcc_unlink_clusters
  1437                              <1> 
  1438                              <1> pass_tcc_unlink_clusters:
  1439 0000CC3D A2[17690100]        <1> 	mov	byte [TCC_FATErr], al
  1440 0000CC42 803D[5A660100]02    <1> 	cmp	byte [FAT_BuffValidData], 2
  1441 0000CC49 750E                <1> 	jne	short loc_tcc_calculate_FAT_freespace
  1442 0000CC4B E89BFDFFFF          <1> 	call	save_fat_buffer
  1443 0000CC50 7307                <1> 	jnc	short loc_tcc_calculate_FAT_freespace
  1444 0000CC52 A2[17690100]        <1> 	mov	byte [TCC_FATErr], al ; Error
  1445                              <1> 	;mov	byte [FAT_BuffValidData], 0
  1446                              <1> 
  1447                              <1> 	; 01/03/2016
  1448 0000CC57 EB12                <1> 	jmp	short loc_tcc_recalculate_FAT_freespace
  1449                              <1> 
  1450                              <1> loc_tcc_calculate_FAT_freespace:
  1451 0000CC59 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter] ; signed (+-) number
  1452 0000CC5E 66BB01FF            <1> 	mov	bx, 0FF01h ; BH = FFh -> ESI = Dos drv desc. table
  1453                              <1> 			   ; BL = 1 -> add cluster
  1454 0000CC62 E819FEFFFF          <1> 	call	calculate_fat_freespace
  1455 0000CC67 21C9                <1> 	and	ecx, ecx ; cx = 0 -> valid free sector count
  1456 0000CC69 7409                <1> 	jz	short pass_truncate_cc_recalc_FAT_freespace
  1457                              <1> 
  1458                              <1> loc_tcc_recalculate_FAT_freespace:
  1459 0000CC6B 66BB00FF            <1> 	mov	bx, 0FF00h ; recalculate !
  1460 0000CC6F E80CFEFFFF          <1> 	call	calculate_fat_freespace
  1461                              <1>               
  1462                              <1> loc_tcc_calculate_FAT_freespace_err:
  1463                              <1> pass_truncate_cc_recalc_FAT_freespace:
  1464 0000CC74 8B0D[62660100]      <1> 	mov	ecx, [FAT_ClusterCounter]
  1465                              <1> 
  1466 0000CC7A 803D[17690100]00    <1> 	cmp	byte [TCC_FATErr], 0
  1467 0000CC81 7608                <1> 	jna	short loc_tcc_unlink_clusters_retn
  1468                              <1> 
  1469                              <1> loc_tcc_unlink_clusters_error:
  1470 0000CC83 0FB605[17690100]    <1> 	movzx	eax, byte [TCC_FATErr]
  1471 0000CC8A F9                  <1> 	stc
  1472                              <1> loc_tcc_unlink_clusters_retn:
  1473 0000CC8B C3                  <1> 	retn
  1474                              <1> 
  1475                              <1> set_fat32_fsinfo_sector_parms:
  1476                              <1> 	; 15/10/2016
  1477                              <1> 	; 23/03/2016
  1478                              <1> 	; 29/02/2016 (TRDOS 386 =  TRDOS v2.0)
  1479                              <1> 	; INPUT ->
  1480                              <1> 	;	ESI = Logical dos drive description table address
  1481                              <1> 	;	[esi+LD_BPB+BPB_Reserved] = Free Cluster Count
  1482                              <1> 	;	[esi+LD_BPB+BPB_Reserved+4] = First Free Cluster 
  1483                              <1> 	; OUTPUT ->
  1484                              <1> 	;	ESI = Logical dos drive description table address
  1485                              <1> 	; 	CF = 0 -> OK..
  1486                              <1> 	; 	CF = 1 -> Error code in EAX (AL)
  1487                              <1> 	;
  1488                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX)
  1489                              <1> 
  1490 0000CC8C E824000000          <1> 	call	get_fat32_fsinfo_sector_parms
  1491 0000CC91 7221                <1> 	jc	short update_fat32_fsinfo_sector_retn
  1492                              <1> 
  1493 0000CC93 8B463A              <1> 	mov	eax, [esi+LD_BPB+BPB_Reserved] ; Free Cluster Count
  1494 0000CC96 8B563E              <1> 	mov	edx, [esi+LD_BPB+BPB_Reserved+4] ; First free Cluster	
  1495                              <1> 
  1496                              <1>         ;mov	ebx, DOSBootSectorBuff
  1497 0000CC99 8983E8010000        <1> 	mov	[ebx+488], eax
  1498 0000CC9F 8993EC010000        <1> 	mov	[ebx+492], edx	
  1499                              <1> 
  1500 0000CCA5 A1[04690100]        <1> 	mov	eax, [CFS_FAT32FSINFOSEC]
  1501 0000CCAA B901000000          <1> 	mov	ecx, 1
  1502 0000CCAF E8FE300000          <1> 	call	disk_write
  1503                              <1> 	;jnc     short update_fat32_fsinfo_sector_retn
  1504                              <1> 
  1505                              <1> 	; 15/10/2016 (1Dh -> 18)
  1506                              <1> 	; 23/03/2016 (1Dh)
  1507                              <1> 	;mov	eax, 18 ; Drive not ready or write error
  1508                              <1> 
  1509                              <1> update_fat32_fsinfo_sector_retn:
  1510 0000CCB4 C3                  <1> 	retn
  1511                              <1> 
  1512                              <1> get_fat32_fsinfo_sector_parms:
  1513                              <1> 	; 15/10/2016
  1514                              <1> 	; 23/03/2016
  1515                              <1> 	; 01/03/2016
  1516                              <1> 	; 29/02/2016 (TRDOS 386 =  TRDOS v2.0)
  1517                              <1> 	; INPUT ->
  1518                              <1> 	;	ESI = Logical dos drive description table address
  1519                              <1> 	; OUTPUT ->
  1520                              <1> 	;	ESI = Logical dos drive description table address
  1521                              <1> 	;	EBX = FSINFO sector buffer address (DOSBootSectorBuff)	
  1522                              <1> 	;	CF = 0 -> OK..
  1523                              <1> 	;	   EAX = FsInfo sector address
  1524                              <1> 	;	   ECX = Free cluster count
  1525                              <1> 	;	   EDX = First free cluster 	
  1526                              <1> 	;	CF = 1 -> Error code in AL (EAX)
  1527                              <1> 	;	   EBX = 0
  1528                              <1> 	;	
  1529                              <1> 	;	[CFS_FAT32FSINFOSEC] = FAT32 FSINFO sector address
  1530                              <1>         ;
  1531                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX)
  1532                              <1> 
  1533 0000CCB5 0FB74636            <1> 	movzx	eax, word [esi+LD_BPB+FAT32_FSInfoSec]
  1534 0000CCB9 03466C              <1> 	add	eax, [esi+LD_StartSector]
  1535 0000CCBC A3[04690100]        <1> 	mov	[CFS_FAT32FSINFOSEC], eax
  1536                              <1> 	
  1537 0000CCC1 BB[56640100]        <1>         mov     ebx, DOSBootSectorBuff
  1538 0000CCC6 B901000000          <1> 	mov	ecx, 1
  1539 0000CCCB E8F1300000          <1> 	call	disk_read
  1540 0000CCD0 7232                <1> 	jc	short loc_read_FAT32_fsinfo_sec_err
  1541                              <1> 
  1542 0000CCD2 BB[56640100]        <1> 	mov	ebx, DOSBootSectorBuff
  1543                              <1> 
  1544 0000CCD7 813B52526141        <1> 	cmp	dword [ebx], 41615252h
  1545 0000CCDD 751E                <1> 	jne	short loc_read_FAT32_fsinfo_sec_stc
  1546                              <1> 
  1547 0000CCDF 81BBE4010000727241- <1> 	cmp	dword [ebx+484], 61417272h
  1547 0000CCE8 61                  <1>
  1548 0000CCE9 7512                <1> 	jne	short loc_read_FAT32_fsinfo_sec_stc
  1549                              <1> 
  1550 0000CCEB A1[04690100]        <1> 	mov	eax, [CFS_FAT32FSINFOSEC]
  1551 0000CCF0 8B8BE8010000        <1> 	mov	ecx, [ebx+488] ; free cluster count
  1552 0000CCF6 8B93EC010000        <1> 	mov	edx, [ebx+492] ; first (next) free cluster	
  1553                              <1> 
  1554 0000CCFC C3                  <1> 	retn
  1555                              <1> 
  1556                              <1> loc_read_FAT32_fsinfo_sec_stc: 
  1557                              <1> 	; 15/10/2016 (0Bh -> 28)
  1558 0000CCFD B81C000000          <1> 	mov	eax, 28 ; Invalid format!
  1559 0000CD02 EB05                <1> 	jmp	short loc_read_FAT32_fsinfo_sec_stc_retn
  1560                              <1> 
  1561                              <1> loc_read_FAT32_fsinfo_sec_err:
  1562                              <1> 	; 15/10/2016 (15h -> 17)
  1563                              <1> 	; 23/03/2016 (15h)
  1564 0000CD04 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error
  1565                              <1> 
  1566                              <1> loc_read_FAT32_fsinfo_sec_stc_retn:
  1567 0000CD09 29DB                <1> 	sub	ebx, ebx ; 0
  1568 0000CD0B F9                  <1> 	stc
  1569 0000CD0C C3                  <1> 	retn
  1570                              <1> 
  1571                              <1> add_new_cluster:
  1572                              <1> 	; 15/10/2016
  1573                              <1> 	; 16/05/2016
  1574                              <1> 	; 18/03/2016, 24/03/2016
  1575                              <1> 	; 11/03/2016 (TRDOS 386 =  TRDOS v2.0)
  1576                              <1> 	; 30/07/2011 (DRV_FAT.ASM)
  1577                              <1> 	; 11/09/2010
  1578                              <1> 	; INPUT ->
  1579                              <1> 	;	ESI = Logical dos drv desc. table address
  1580                              <1> 	;	EAX = Last cluster
  1581                              <1> 	; OUTPUT ->
  1582                              <1> 	;	ESI = Logical dos drv desc. table address
  1583                              <1> 	;	EAX = New Last cluster (next cluster)
  1584                              <1> 	;	cf = 1 -> error code in EAX (AL)
  1585                              <1> 	;	cf = 1 -> DX = sectors per cluster
  1586                              <1> 	;	ECX = Free sectors
  1587                              <1> 	; NOTE:
  1588                              <1> 	; This procedure does not update lm date&time !
  1589                              <1> 	;
  1590                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX, EDI)
  1591                              <1> 	;
  1592                              <1> 
  1593 0000CD0D A3[346A0100]        <1> 	mov	[FAT_anc_LCluster], eax
  1594                              <1> 	
  1595 0000CD12 E844F9FFFF          <1> 	call	get_first_free_cluster
  1596 0000CD17 720B                <1> 	jc	short loc_add_new_cluster_retn
  1597                              <1> 	; EAX >= 2 and EAX < FFFFFFFFh is valid
  1598                              <1> 
  1599 0000CD19 89C2                <1> 	mov	edx, eax
  1600                              <1> 
  1601 0000CD1B 42                  <1> 	inc	edx
  1602                              <1> 	;jnz	short loc_add_new_cluster_check_ffc_eax
  1603 0000CD1C 7516                <1> 	jnz	short loc_add_new_cluster_save_fcc
  1604                              <1> 
  1605                              <1> loc_add_new_cluster_no_disk_space_retn:
  1606 0000CD1E B827000000          <1> 	mov	eax, 27h ; MSDOS err => insufficient disk space
  1607                              <1> loc_add_new_cluster_stc_retn:
  1608 0000CD23 F9                  <1> 	stc
  1609                              <1> loc_add_new_cluster_retn:
  1610 0000CD24 0FB65E13            <1> 	movzx	ebx, byte [esi+LD_BPB+SecPerClust]
  1611 0000CD28 8B4E74              <1> 	mov	ecx, [esi+LD_FreeSectors]
  1612                              <1> 	;xor	edx, edx
  1613                              <1> 	;stc
  1614 0000CD2B C3                  <1> 	retn
  1615                              <1> 
  1616                              <1> loc_anc_invalid_format_stc_retn:
  1617 0000CD2C F9                  <1> 	stc
  1618                              <1> loc_add_new_cluster_invalid_format_retn:
  1619                              <1> 	; 15/10/2016 (0Bh -> 28)
  1620 0000CD2D B81C000000          <1> 	mov	eax, 28 ; Invalid format
  1621 0000CD32 EBF0                <1> 	jmp	short loc_add_new_cluster_retn 
  1622                              <1> 
  1623                              <1> ;loc_add_new_cluster_check_ffc_eax:
  1624                              <1> ;	cmp	eax, 2
  1625                              <1> ;	jb	short loc_add_new_cluster_invalid_format_retn
  1626                              <1> 
  1627                              <1> loc_add_new_cluster_save_fcc:  
  1628 0000CD34 A3[386A0100]        <1> 	mov	[FAT_anc_FFCluster], eax
  1629                              <1> 
  1630 0000CD39 83E802              <1> 	sub	eax, 2
  1631 0000CD3C 0FB65E13            <1>         movzx   ebx, byte [esi+LD_BPB+SecPerClust]
  1632 0000CD40 F7E3                <1> 	mul	ebx
  1633 0000CD42 09D2                <1> 	or	edx, edx
  1634 0000CD44 75E6                <1> 	jnz	short loc_anc_invalid_format_stc_retn
  1635                              <1> 
  1636                              <1> loc_add_new_cluster_allocate_cluster:
  1637                              <1> 	; 18/03/2016
  1638 0000CD46 92                  <1> 	xchg	edx, eax ; eax = 0
  1639                              <1> 	; 16/05/2016
  1640                              <1> 	;cmp	[ClusterBuffer_Valid], al ; 0
  1641                              <1> 	;jna	short loc_anc_clear_cluster_buffer
  1642                              <1> 	;; 'copy' command, 
  1643                              <1> 	;; writing destination file clust after reading source file clust
  1644                              <1> 	;mov	[ClusterBuffer_Valid], al ; 0 ; reset
  1645                              <1> 	;jmp	short loc_add_new_cluster_write_nc_to_disk
  1646                              <1> 
  1647                              <1> loc_anc_clear_cluster_buffer:
  1648                              <1> 	; 11/03/2016
  1649                              <1> 	; Clear buffer
  1650 0000CD47 BF00000700          <1> 	mov	edi, Cluster_Buffer ; 70000h (for current TRDOS 386 version)
  1651 0000CD4C 89D9                <1> 	mov	ecx, ebx ; sector count
  1652 0000CD4E C1E107              <1> 	shl	ecx, 7 ; 1 sector = 512 bytes -> 128 double words
  1653                              <1> 	;xor	eax, eax ; 0
  1654 0000CD51 F3AB                <1> 	rep	stosd
  1655                              <1> 
  1656                              <1> loc_add_new_cluster_write_nc_to_disk:
  1657                              <1> 	; 11/03/2016
  1658                              <1> 	;xchg	eax, edx ; edx = 0, eax = sector offset
  1659 0000CD53 89D0                <1> 	mov	eax, edx
  1660 0000CD55 034668              <1>         add     eax, [esi+LD_DATABegin]
  1661 0000CD58 72D3                <1> 	jc	short loc_add_new_cluster_invalid_format_retn 
  1662                              <1> 		
  1663 0000CD5A 89D9                <1> 	mov	ecx, ebx ; ECX = sectors per cluster (<256)
  1664 0000CD5C BB00000700          <1> 	mov	ebx, Cluster_Buffer
  1665 0000CD61 E84C300000          <1> 	call	disk_write
  1666 0000CD66 7307                <1> 	jnc	short loc_add_new_cluster_update_fat_nlc
  1667                              <1> 	
  1668                              <1> 	; 15/10/2016 (1Dh -> 18)
  1669 0000CD68 B812000000          <1> 	mov	eax, 18 ; Write Error
  1670 0000CD6D EBB4                <1> 	jmp	short loc_add_new_cluster_stc_retn
  1671                              <1> 
  1672                              <1> loc_add_new_cluster_update_fat_nlc:
  1673 0000CD6F A1[386A0100]        <1> 	mov	eax, [FAT_anc_FFCluster]
  1674 0000CD74 31C9                <1> 	xor	ecx, ecx
  1675 0000CD76 890D[62660100]      <1> 	mov	[FAT_ClusterCounter], ecx ; 0 ; reset
  1676 0000CD7C 49                  <1> 	dec	ecx ; 0FFFFFFFFh
  1677 0000CD7D E8ACF9FFFF          <1> 	call	update_cluster
  1678 0000CD82 7304                <1> 	jnc	short loc_add_new_cluster_update_fat_plc
  1679 0000CD84 09C0                <1> 	or	eax, eax ;EAX = 0 -> cluster value is 0 or eocc
  1680 0000CD86 759B                <1> 	jnz	short loc_add_new_cluster_stc_retn
  1681                              <1> 
  1682                              <1> loc_add_new_cluster_update_fat_plc:
  1683 0000CD88 A1[346A0100]        <1> 	mov	eax, [FAT_anc_LCluster]
  1684 0000CD8D 8B0D[386A0100]      <1> 	mov	ecx, [FAT_anc_FFCluster]
  1685 0000CD93 E896F9FFFF          <1> 	call	update_cluster
  1686 0000CD98 7314                <1> 	jnc	short loc_add_new_cluster_save_fat_buffer
  1687 0000CD9A 09C0                <1> 	or	eax, eax ; EAX = 0 -> cluster value is 0 or eocc
  1688 0000CD9C 7410                <1> 	jz	short loc_add_new_cluster_save_fat_buffer
  1689                              <1> 
  1690                              <1> loc_anc_save_fat_buffer_err_retn:
  1691                              <1> 	;cmp	byte [FAT_ClusterCounter], 1
  1692                              <1> 	;jb	short loc_add_new_cluster_retn
  1693                              <1> 
  1694 0000CD9E 66BB00FF            <1> 	mov	bx, 0FF00h ; recalculate free space (BL = 0)
  1695                              <1> 			   ; (BH = FFh -> Use ESI as Drv Param. Tbl.)
  1696 0000CDA2 50                  <1> 	push	eax
  1697 0000CDA3 E8D8FCFFFF          <1> 	call	calculate_fat_freespace
  1698 0000CDA8 58                  <1> 	pop	eax
  1699 0000CDA9 E975FFFFFF          <1>         jmp     loc_add_new_cluster_stc_retn
  1700                              <1> 
  1701                              <1> loc_add_new_cluster_save_fat_buffer:
  1702                              <1> 	;cmp	byte [FAT_BuffValidData], 2
  1703                              <1> 	;jne	short loc_add_new_cluster_calc_FAT_freespace 
  1704                              <1> 	;Byte [FAT_BuffValidData] =  2 
  1705 0000CDAE E838FCFFFF          <1> 	call	save_fat_buffer
  1706 0000CDB3 72E9                <1> 	jc	short loc_anc_save_fat_buffer_err_retn
  1707                              <1> 
  1708                              <1> loc_add_new_cluster_calc_FAT_freespace:
  1709                              <1> 	;mov	eax, 1 ; Only one Cluster
  1710 0000CDB5 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  1711 0000CDBA 66BB01FF            <1> 	mov	bx, 0FF01h ; BH = FFh -> ESI -> Dos drv desc. table
  1712                              <1> 		; BL = 1 -> add cluster
  1713 0000CDBE B301                <1> 	mov	bl, 01h ; BL = 1 -> add clusters
  1714                              <1> 	; NOTE: EAX value will be added to Free Cluster Count
  1715                              <1> 	; (Free Cluster Count is decreased when EAX value is negative)
  1716 0000CDC0 E8BBFCFFFF          <1>         call    calculate_fat_freespace
  1717                              <1> 	;ECX = 0 -> no error, ECX > 0 -> error or invalid return
  1718 0000CDC5 21C9                <1> 	and	ecx, ecx ; ECX = 0 -> valid free sector count
  1719 0000CDC7 7409                <1> 	jz	short loc_add_new_cluster_return_cluster_number
  1720                              <1> 
  1721                              <1> loc_add_new_cluster_recalc_FAT_freespace:
  1722 0000CDC9 66BB00FF            <1> 	mov	bx, 0FF00h  ; recalculate free space
  1723 0000CDCD E8AEFCFFFF          <1>         call    calculate_fat_freespace
  1724                              <1> 	; cf = 0
  1725                              <1> loc_add_new_cluster_return_cluster_number:
  1726 0000CDD2 89C1                <1> 	mov	ecx, eax ; Free sector count
  1727 0000CDD4 A1[386A0100]        <1> 	mov	eax, [FAT_anc_FFCluster]
  1728 0000CDD9 0FB65E13            <1> 	movzx	ebx, byte [esi+LD_BPB+SecPerClust]
  1729                              <1> 	;mov	edi, Cluster_Buffer
  1730 0000CDDD 31D2                <1> 	xor	edx, edx
  1731 0000CDDF C3                  <1>         retn
  1732                              <1> 
  1733                              <1> write_cluster:
  1734                              <1> 	; 15/10/2016
  1735                              <1> 	; 21/03/2016 (TRDOS 386 =  TRDOS v2.0)
  1736                              <1> 	;
  1737                              <1> 	; INPUT ->
  1738                              <1> 	;	EAX = Cluster Number (Sector index for SINGLIX FS)
  1739                              <1> 	;	ESI = Logical DOS Drive Description Table address
  1740                              <1> 	;	EBX = Cluster (File R/W) Buffer address (max. 64KB)
  1741                              <1> 	;	Only for SINGLIX FS:
  1742                              <1> 	;	EDX = File Number (The 1st FDT address) 
  1743                              <1> 	; OUTPUT ->
  1744                              <1> 	;	cf = 1 -> Cluster can not be written onto disk
  1745                              <1> 	;	    EAX > 0 -> Error number
  1746                              <1> 	;	cf = 0 -> Cluster has been written successfully
  1747                              <1> 	;
  1748                              <1> 	; (Modified registers: EAX, ECX, EBX, EDX)
  1749                              <1> 	
  1750 0000CDE0 0FB64E13            <1> 	movzx	ecx, byte [esi+LD_BPB+BPB_SecPerClust] 
  1751                              <1> 	; CL = 1 = [esi+LD_FS_Reserved2] ; SectPerClust for Singlix FS
  1752                              <1> 
  1753                              <1> write_file_sectors: ; 16/03/2016
  1754 0000CDE4 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  1755 0000CDE8 761C                <1> 	jna	short write_fs_cluster
  1756                              <1> 
  1757                              <1> write_fat_file_sectors: 
  1758 0000CDEA 83E802              <1> 	sub	eax, 2 ; Beginning cluster number is always 2
  1759 0000CDED 0FB65613            <1> 	movzx	edx, byte [esi+LD_BPB+BPB_SecPerClust] ; 18/03/2016 
  1760 0000CDF1 F7E2                <1> 	mul	edx
  1761 0000CDF3 034668              <1> 	add	eax, [esi+LD_DATABegin] ; absolute address of the cluster
  1762                              <1> 
  1763                              <1> 	; EAX = Disk sector address
  1764                              <1> 	; ECX = Sector count
  1765                              <1> 	; EBX = Buffer address
  1766                              <1> 	; (EDX = 0)
  1767                              <1> 	; ESI = Logical DOS drive description table address	
  1768                              <1> 
  1769 0000CDF6 E8B72F0000          <1> 	call	disk_write
  1770 0000CDFB 7306                <1> 	jnc	short wclust_retn
  1771                              <1> 	
  1772                              <1> 	; 15/10/2016 (1Dh -> 18)
  1773 0000CDFD B812000000          <1> 	mov	eax, 18 ; Drive not ready or write error !
  1774 0000CE02 C3                  <1> 	retn
  1775                              <1> 
  1776                              <1> wclust_retn:
  1777 0000CE03 29C0                <1> 	sub	eax, eax ; 0
  1778 0000CE05 C3                  <1> 	retn
  1779                              <1> 
  1780                              <1> write_fs_cluster:
  1781                              <1> 	; 21/03/2016 (TRDOS 386 =  TRDOS v2.0)
  1782                              <1> 	; Singlix FS
  1783                              <1> 	
  1784                              <1> 	; EAX = Cluster number is sector index number of the file (eax)
  1785                              <1> 	
  1786                              <1> 	; EDX = File number is the first File Descriptor Table address 
  1787                              <1> 	;	of the file. (Absolute address of the FDT).
  1788                              <1> 	
  1789                              <1> 	; eax = sector index (0 for the first sector)
  1790                              <1> 	; edx = FDT0 address
  1791                              <1> 		; 64 KB buffer = 128 sectors (limit) 
  1792 0000CE06 B980000000          <1> 	mov	ecx, 128 ; maximum count of sectors (before eof) 
  1793 0000CE0B E801000000          <1> 	call	write_fs_sectors
  1794 0000CE10 C3                  <1> 	retn
  1795                              <1> 
  1796                              <1> write_fs_sectors:
  1797                              <1> 	; 21/03/2016 (TRDOS 386 =  TRDOS v2.0)
  1798 0000CE11 F9                  <1> 	stc
  1799 0000CE12 C3                  <1> 	retn
  1800                              <1> 
  1801                              <1> get_cluster_by_index:
  1802                              <1> 	; 29/04/2016 (TRDOS 386 =  TRDOS v2.0)
  1803                              <1> 	; INPUT ->
  1804                              <1> 	; 	EAX = Beginning cluster
  1805                              <1> 	; 	EDX = Sector index in disk/file section
  1806                              <1> 	;	      (Only for SINGLIX file system!)
  1807                              <1> 	; 	ECX = Cluster sequence number after the beginning cluster
  1808                              <1> 	; 	ESI = Logical DOS Drive Description Table address
  1809                              <1> 	; OUTPUT ->
  1810                              <1> 	;	EAX = Cluster number 
  1811                              <1> 	;	cf = 1 -> Error code in AL (EAX)
  1812                              <1> 	;
  1813                              <1> 	;(Modified registers: EAX, ECX, EBX, EDX)
  1814                              <1> 	;	
  1815 0000CE13 807E0301            <1> 	cmp	byte [esi+LD_FATType], 1
  1816 0000CE17 721E                <1>         jb      short get_fs_section_by_index 
  1817                              <1> 
  1818 0000CE19 3B4E78              <1> 	cmp	ecx, [esi+LD_Clusters]
  1819 0000CE1C 7207                <1> 	jb	short gcbi_1
  1820                              <1> gcbi_0:
  1821 0000CE1E F9                  <1> 	stc
  1822 0000CE1F B823000000          <1> 	mov	eax, 23h ; Cluster not available ! 
  1823                              <1> 			 ; MSDOS error code: FCB unavailable
  1824 0000CE24 C3                  <1> 	retn
  1825                              <1> gcbi_1:
  1826 0000CE25 51                  <1> 	push	ecx
  1827 0000CE26 E8D9F5FFFF          <1> 	call	get_next_cluster
  1828 0000CE2B 59                  <1> 	pop	ecx
  1829 0000CE2C 7203                <1> 	jc	short gcbi_3
  1830 0000CE2E E2F5                <1> 	loop	gcbi_1
  1831                              <1> gcbi_2:
  1832 0000CE30 C3                  <1> 	retn
  1833                              <1> gcbi_3:
  1834 0000CE31 09C0                <1> 	or	eax, eax
  1835 0000CE33 74E9                <1> 	jz	short gcbi_0
  1836 0000CE35 F5                  <1> 	cmc 	; stc
  1837 0000CE36 C3                  <1> 	retn
  1838                              <1> 
  1839                              <1> get_fs_section_by_index:
  1840                              <1> 	; 29/04/2016 (TRDOS 386 =  TRDOS v2.0)
  1841                              <1> 	; INPUT ->
  1842                              <1> 	; 	EAX = Beginning FDT number/address
  1843                              <1> 	; 	EDX = Sector index in disk/file section
  1844                              <1> 	; 	ECX = Sector sequence number after the beginning FDT
  1845                              <1> 	; 	ESI = Logical DOS Drive Description Table address
  1846                              <1> 	; OUTPUT ->
  1847                              <1> 	; 	EAX = FDT number/address
  1848                              <1> 	; 	EDX = Sector index of the section (0,1,2,3,4...)
  1849                              <1> 	;	cf = 1 -> Error code in AL (EAX)
  1850                              <1> 	;
  1851                              <1> 	;(Modified registers: EAX, ECX, EBX, EDX)
  1852                              <1> 	;
  1853 0000CE37 B8FFFFFFFF          <1> 	mov	eax, 0FFFFFFFFh
  1854 0000CE3C C3                  <1> 	retn
  1855                              <1> 
  1856                              <1> get_last_section:
  1857                              <1> 	; 22/10/2016 (TRDOS 386 =  TRDOS v2.0)	
  1858                              <1> 	; INPUT ->
  1859                              <1> 	; 	EAX = (The 1st) FDT number/address
  1860                              <1> 	; 	ESI = Logical DOS Drive Description Table address
  1861                              <1> 	; OUTPUT ->
  1862                              <1> 	; 	EAX = FDT number/address of the last section
  1863                              <1> 	; 	EDX = Last sector of the section (0,1,2,3,4...)
  1864                              <1> 	;	[glc_index] = sector index number of the last sector
  1865                              <1> 	;		      (for file, not for the last section)  	
  1866                              <1> 	;		   	
  1867                              <1> 	;	cf = 1 -> Error code in AL (EAX)
  1868                              <1> 	;
  1869                              <1> 	;(Modified registers: EAX, ECX, EBX, EDX)
  1870                              <1> 	;
  1871 0000CE3D B800000000          <1> 	mov	eax, 0
  1872 0000CE42 BA00000000          <1> 	mov	edx, 0
  1873 0000CE47 C3                  <1> 	retn
  2866                                  %include 'trdosk6.s' ; 24/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.3) - MAIN PROGRAM : trdosk6.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 23/11/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    11                              <1> ; u1.s (27/17/2015), u2.s (03/01/2016)
    12                              <1> ; ****************************************************************************
    13                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    14                              <1> ; TRDOS2.ASM (09/11/2011)
    15                              <1> ; ----------------------------------------------------------------------------
    16                              <1> ; INT_21H.ASM (c) 2009-2011 Erdogan TAN  [14/11/2009] Last Update: 08/11/2011
    17                              <1> 
    18                              <1> sysent: ; < enter to system call >
    19                              <1> 	; 17/03/2017
    20                              <1> 	; 03/03/2017
    21                              <1> 	; 19/02/2017
    22                              <1> 	; 13/01/2017
    23                              <1> 	; 06/06/2016
    24                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
    25                              <1> 	; 16/04/2015 - 19/10/2015 (Retro UNIX 386 v1)
    26                              <1> 	; 10/04/2013 - 18/01/2014 (Retro UNIX 8086 v1)
    27                              <1> 	;
    28                              <1> 	; 'unkni' or 'sysent' is sytem entry from various traps. 
    29                              <1> 	; The trap type is determined and an indirect jump is made to 
    30                              <1> 	; the appropriate system call handler. If there is a trap inside
    31                              <1> 	; the system a jump to panic is made. All user registers are saved 
    32                              <1> 	; and u.sp points to the end of the users stack. The sys (trap)
    33                              <1> 	; instructor is decoded to get the the system code part (see
    34                              <1> 	; trap instruction in the PDP-11 handbook) and from this 
    35                              <1> 	; the indirect jump address is calculated. If a bad system call is
    36                              <1> 	; made, i.e., the limits of the jump table are exceeded, 'badsys'
    37                              <1> 	; is called. If the call is legitimate control passes to the
    38                              <1> 	; appropriate system routine.
    39                              <1> 	;
    40                              <1> 	; Calling sequence:
    41                              <1> 	;	Through a trap caused by any sys call outside the system.
    42                              <1> 	; Arguments:
    43                              <1> 	;	Arguments of particular system call.	
    44                              <1> 	; ...............................................................
    45                              <1> 	;	
    46                              <1> 	; Retro UNIX 8086 v1 modification: 
    47                              <1> 	;       System call number is in EAX register.
    48                              <1> 	;
    49                              <1> 	;       Other parameters are in EDX, EBX, ECX, ESI, EDI, EBP
    50                              <1> 	;	registers depending of function details.
    51                              <1>   	;
    52                              <1> 	; 16/04/2015
    53 0000CE48 368925[5C030300]    <1>         mov     [ss:u.sp], esp ; Kernel stack points to return address
    54                              <1> 
    55                              <1> 	; save user registers
    56 0000CE4F 1E                  <1> 	push	ds
    57 0000CE50 06                  <1> 	push	es
    58 0000CE51 0FA0                <1> 	push	fs
    59 0000CE53 0FA8                <1> 	push	gs
    60 0000CE55 60                  <1> 	pushad  ; eax, ecx, edx, ebx, esp -before pushad-, ebp, esi, edi
    61                              <1> 	;
    62                              <1> 	; ESPACE = [ss:u.sp] - esp ; 4*12 = 48 ; 17/09/2015 ; 06/06/2016
    63                              <1> 	; 	(ESPACE is size of space in kernel stack 
    64                              <1> 	;	for saving/restoring user registers.)
    65                              <1> 	;
    66 0000CE56 50                  <1> 	push	eax ; 01/07/2015
    67 0000CE57 66B81000            <1> 	mov     ax, KDATA
    68 0000CE5B 8ED8                <1>         mov     ds, ax
    69 0000CE5D 8EC0                <1>         mov     es, ax
    70 0000CE5F 8EE0                <1>         mov     fs, ax
    71 0000CE61 8EE8                <1>         mov     gs, ax
    72 0000CE63 A1[805E0100]        <1> 	mov	eax, [k_page_dir]
    73 0000CE68 0F22D8              <1> 	mov	cr3, eax
    74 0000CE6B 58                  <1> 	pop	eax ; 01/07/2015
    75                              <1> 	; 19/10/2015
    76 0000CE6C FC                  <1> 	cld
    77                              <1> 	;
    78 0000CE6D FE05[5B030300]      <1> 	inc	byte [sysflg]
    79                              <1> 		; incb sysflg / indicate a system routine is in progress
    80 0000CE73 FB                  <1>         sti 	; 18/01/2014
    81 0000CE74 0F85DF9DFFFF        <1> 	jnz     panic ; 24/05/2013
    82                              <1> 		; beq 1f
    83                              <1> 		; jmp panic ; / called if trap inside system
    84                              <1> ;1:
    85                              <1> 	; 17/03/2017
    86 0000CE7A 80642438FE          <1> 	and	byte [esp+ESPACE+8], ~1 ; clear carry flag
    87                              <1> 
    88                              <1> 	; 16/04/2015
    89 0000CE7F A3[64030300]        <1> 	mov	[u.r0], eax
    90 0000CE84 8925[60030300]      <1> 	mov	[u.usp], esp ; kernel stack points to user's registers
    91                              <1> 
    92                              <1> 	; 13/01/2017 (TRDOS 386 Feaure only !)
    93 0000CE8A 803D[D4030300]00    <1> 	cmp	byte [u.t_lock], 0 ; timer interrupt lock ?
    94 0000CE91 0F879D010000        <1> 	ja	sysrele		   ; yes, sys release only !!!
    95                              <1> 
    96                              <1> 		; mov $s.syst+2,clockp
    97                              <1> 		; mov r0,-(sp) / save user registers 
    98                              <1> 		; mov sp,u.r0 / pointer to bottom of users stack 
    99                              <1> 			   ; / in u.r0
   100                              <1> 		; mov r1,-(sp)
   101                              <1> 		; mov r2,-(sp)
   102                              <1> 		; mov r3,-(sp)
   103                              <1> 		; mov r4,-(sp)
   104                              <1> 		; mov r5,-(sp)
   105                              <1> 		; mov ac,-(sp) / "accumulator" register for extended
   106                              <1> 		             ; / arithmetic unit
   107                              <1> 		; mov mq,-(sp) / "multiplier quotient" register for the
   108                              <1> 		             ; / extended arithmetic unit
   109                              <1> 		; mov sc,-(sp) / "step count" register for the extended
   110                              <1> 		             ; / arithmetic unit
   111                              <1> 		; mov sp,u.sp / u.sp points to top of users stack
   112                              <1> 		; mov 18.(sp),r0 / store pc in r0
   113                              <1> 		; mov -(r0),r0 / sys inst in r0      10400xxx
   114                              <1> 		; sub $sys,r0 / get xxx code
   115 0000CE97 C1E002              <1> 	shl	eax, 2
   116                              <1> 		; asl r0 / multiply by 2 to jump indirect in bytes
   117 0000CE9A 3DB8000000          <1> 	cmp	eax, end_of_syscalls - syscalls
   118                              <1> 		; cmp r0,$2f-1f / limit of table (35) exceeded
   119                              <1> 	;jnb	short badsys
   120                              <1> 		; bhis badsys / yes, bad system call
   121 0000CE9F F5                  <1> 	cmc
   122 0000CEA0 9C                  <1> 	pushf	
   123 0000CEA1 50                  <1> 	push	eax
   124 0000CEA2 8B2D[5C030300]      <1>  	mov 	ebp, [u.sp] ; Kernel stack at the beginning of sys call
   125 0000CEA8 B0FE                <1> 	mov	al, 0FEh ; 11111110b
   126 0000CEAA 1400                <1> 	adc	al, 0 ; al = al + cf
   127 0000CEAC 204508              <1> 	and	[ebp+8], al ; flags (reset carry flag)
   128                              <1> 		; bic $341,20.(sp) / set users processor priority to 0 
   129                              <1> 				 ; / and clear carry bit
   130 0000CEAF 5D                  <1> 	pop	ebp ; eax
   131 0000CEB0 9D                  <1> 	popf
   132 0000CEB1 0F8208020000        <1>         jc      badsys
   133 0000CEB7 A1[64030300]        <1> 	mov	eax, [u.r0]
   134                              <1> 	; system call registers: EAX, EDX, ECX, EBX, ESI, EDI
   135 0000CEBC FFA5[C2CE0000]      <1> 	jmp	dword [ebp+syscalls]
   136                              <1> 		; jmp *1f(r0) / jump indirect thru table of addresses
   137                              <1> 		            ; / to proper system routine.
   138                              <1> syscalls: ; 1:
   139                              <1> 	; 31/12/2017
   140                              <1> 	; 28/02/2017
   141                              <1> 	; 20/02/2017
   142                              <1> 	; 19/02/2017
   143                              <1> 	; 15/10/2016
   144                              <1> 	; 20/05/2016
   145                              <1> 	; 19/05/2016
   146                              <1> 	; 16/05/2016
   147                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   148                              <1> 	; 21/09/2015
   149                              <1> 	; 01/07/2015
   150                              <1> 	; 16/04/2015 (32 bit address modification) 
   151 0000CEC2 [A6EC0000]          <1> 	dd sysver	; 0 ; Get TRDOS 386 version number (v2.0)	
   152 0000CEC6 [21D10000]          <1> 	dd sysexit 	; 1
   153 0000CECA [F6D20000]          <1> 	dd sysfork 	; 2
   154 0000CECE [29D70000]          <1> 	dd sysread 	; 3
   155 0000CED2 [48D70000]          <1> 	dd syswrite 	; 4
   156 0000CED6 [DFD40000]          <1> 	dd sysopen 	; 5
   157 0000CEDA [00D70000]          <1> 	dd sysclose 	; 6
   158 0000CEDE [78D20000]          <1> 	dd syswait 	; 7
   159 0000CEE2 [0ED40000]          <1> 	dd syscreat 	; 8
   160 0000CEE6 [FAFA0000]          <1> 	dd sysrename	; 9  ; TRDOS 386, Rename File (31/12/2017)
   161 0000CEEA [75F60000]          <1> 	dd sysdelete	; 10 ; TRDOS 386, Delete File (29/12/2017)
   162 0000CEEE [89E00000]          <1> 	dd sysexec 	; 11
   163 0000CEF2 [9FF70000]          <1> 	dd syschdir 	; 12
   164 0000CEF6 [64F90000]          <1> 	dd systime 	; 13 ; TRDOS 386, Get Sys Date&Time (30/12/2017)
   165 0000CEFA [C2D60000]          <1> 	dd sysmkdir 	; 14
   166 0000CEFE [D3F70000]          <1> 	dd syschmod 	; 15 ; TRDOS 386, Change Attributes (30/12/2017) 
   167 0000CF02 [DCF60000]          <1> 	dd sysrmdir 	; 16 ; TRDOS 386, Remove Directory (29/12/2017)
   168 0000CF06 [64E30000]          <1> 	dd sysbreak 	; 17
   169 0000CF0A [B9F80000]          <1> 	dd sysdrive 	; 18 ; TRDOS 386, Get/Set Current Drv (30/12/2017) 
   170 0000CF0E [A5E30000]          <1> 	dd sysseek 	; 19
   171 0000CF12 [B7E30000]          <1> 	dd systell 	; 20
   172 0000CF16 [1BFC0000]          <1> 	dd sysmem 	; 21 ; TRDOS 386, Get Total&Free Mem (31/12/2017)
   173 0000CF1A [51FC0000]          <1> 	dd sysprompt 	; 22 ; TRDOS 386, Change Cmd Prompt (31/12/2017)
   174 0000CF1E [93FC0000]          <1> 	dd syspath 	; 23 ; TRDOS 386, Get/Set Run Path (31/12/2017)
   175 0000CF22 [00FD0000]          <1> 	dd sysenv 	; 24 ; TRDOS 386, Get/Set Env Vars (31/12/2017)
   176 0000CF26 [E5F90000]          <1> 	dd sysstime 	; 25 ; TRDOS 386, Set Sys Date&Time (30/12/2017)
   177 0000CF2A [1DE40000]          <1> 	dd sysquit 	; 26
   178 0000CF2E [11E40000]          <1> 	dd sysintr 	; 27
   179 0000CF32 [08F90000]          <1> 	dd sysdir 	; 28 ; TRDOS 386, Get Curr Drive&Dir (30/12/2017) 
   180 0000CF36 [DFD70000]          <1> 	dd sysemt 	; 29
   181 0000CF3A [43F90000]          <1> 	dd sysldrvt	; 30 ; TRDOS 386, Get Logical DOS DDT (30/12/2017)
   182 0000CF3E [90D90000]          <1> 	dd sysvideo 	; 31 ; TRDOS 386 Video Functions (16/05/2016)
   183 0000CF42 [D0060100]          <1> 	dd sysaudio 	; 32 ; TRDOS 386 Audio Functions (16/05/2016)
   184 0000CF46 [F8D70000]          <1> 	dd systimer 	; 33 ; TRDOS 386 Timer Functions (18/05/2016)
   185 0000CF4A [5EE40000]          <1> 	dd syssleep 	; 34 ; Retro UNIX 8086 v1 feature only !
   186                              <1> 			     ; 11/06/2014
   187 0000CF4E [8DE40000]          <1> 	dd sysmsg	; 35 ; Retro UNIX 386 v1 feature only !
   188                              <1> 			     ; 01/07/2015
   189 0000CF52 [64E50000]          <1> 	dd sysgeterr	; 36 ; Retro UNIX 386 v1 feature only !
   190                              <1> 			     ; 21/09/2015 - get last error number
   191 0000CF56 [4CF60000]          <1> 	dd sysfpstat	; 37 ; TRDOS 386 FPU state option (28/02/2017)
   192 0000CF5A [B5EC0000]          <1> 	dd syspri 	; 38 ; change priority - TRDOS 386 (20/05/2016)
   193 0000CF5E [34D00000]          <1> 	dd sysrele	; 39 ; TRDOS 386 (19/05/2016) (0 -> 39)
   194 0000CF62 [E8ED0000]          <1> 	dd sysfff	; 40 ; Find First File - TRDOS 386 (15/10/2016)
   195 0000CF66 [C7EE0000]          <1> 	dd sysfnf	; 41 ; Find Next File - TRDOS 386 (15/10/2016)
   196 0000CF6A [37F50000]          <1> 	dd sysalloc	; 42 ; Allocate contiguous memory block/pages
   197                              <1> 			     ; TRDOS 386 (19/02/2017) DMA buff fuctions		
   198 0000CF6E [F5F50000]          <1> 	dd sysdalloc	; 43 ; Deallocate contiguous memory block/pages
   199                              <1> 			     ; TRDOS 386 (19/02/2017) DMA buff fuctions
   200 0000CF72 [30F60000]          <1> 	dd syscalbac	; 44 ; IRQ Callback and Signal Response Byte
   201                              <1> 			     ; service setup - TRDOS 386 (20/02/2017)
   202                              <1> 			     ; 28/08/2017 (20/08/2017)	
   203 0000CF76 [610F0100]          <1> 	dd sysdma	; 45 ; TRDOS 386 - (ISA) DMA service
   204                              <1> 	
   205                              <1> end_of_syscalls:
   206                              <1> 
   207                              <1> error:
   208                              <1> 	; 18/05/2016
   209                              <1> 	; 13/05/2016
   210                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   211                              <1> 	; 16/04/2015 - 17/09/2015 (Retro UNIX 386 v1)
   212                              <1> 	; 10/04/2013 - 07/08/2013 (Retro UNIX 8086 v1)
   213                              <1> 	;
   214                              <1> 	; 'error' merely sets the error bit off the processor status (c-bit)
   215                              <1> 	; then falls right into the 'sysret', 'sysrele' return sequence.
   216                              <1> 	;
   217                              <1> 	; INPUTS -> none
   218                              <1> 	; OUTPUTS ->
   219                              <1> 	;	processor status - carry (c) bit is set (means error)
   220                              <1> 	;
   221                              <1> 	; 26/05/2013 (Stack pointer must be reset here! 
   222                              <1> 	; 	      Because, jumps to error procedure
   223                              <1> 	;	      disrupts push-pop nesting balance)
   224                              <1> 	;
   225 0000CF7A 8B2D[5C030300]      <1> 	mov	ebp, [u.sp] ; interrupt (system call) return (iretd) address
   226 0000CF80 804D0801            <1> 	or	byte [ebp+8], 1  ; set carry bit of flags register
   227                              <1> 				 ; (system call will return with cf = 1)
   228                              <1> 		; bis $1,20.(r1) / set c bit in processor status word below
   229                              <1> 		               ; / users stack
   230                              <1> 	; 17/09/2015
   231 0000CF84 83ED30              <1> 	sub	ebp, ESPACE ; 48 ; total size of stack frame ('sysdefs.inc')
   232                              <1> 				 ; for saving/restoring user registers	
   233                              <1> 	;cmp	ebp, [u.usp]
   234                              <1> 	;je	short err0	
   235 0000CF87 892D[60030300]      <1> 	mov	[u.usp], ebp
   236                              <1> ;err0:
   237                              <1> 	; 01/09/2015
   238 0000CF8D 8B25[60030300]      <1> 	mov	esp, [u.usp] 	    ; Retro Unix 8086 v1 modification!
   239                              <1> 				    ; 10/04/2013
   240                              <1> 				    ; (If an I/O error occurs during disk I/O,
   241                              <1> 				    ; related procedures will jump to 'error'
   242                              <1> 				    ; procedure directly without returning to 
   243                              <1> 				    ; the caller procedure. So, stack pointer
   244                              <1>                                     ; must be restored here.)
   245                              <1> 	; 13/05/2016
   246                              <1> 	; NOTE: (The last) error code is in 'u.error', it can be retrieved by
   247                              <1> 	;	'get last error' system call later. 	
   248                              <1> 
   249                              <1> 	; 03/09/2015 - 09/06/2015 - 07/08/2013
   250 0000CF93 C605[C6030300]00    <1> 	mov 	byte [u.kcall], 0 ; namei_r, mkdir_w reset
   251                              <1> 
   252                              <1> sysret: ; < return from system call>
   253                              <1> 	; 01/03/2017
   254                              <1> 	; 28/02/2017
   255                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   256                              <1> 	; 16/04/2015 - 10/09/2015 (Retro UNIX 386 v1)
   257                              <1> 	; 10/04/2013 - 23/02/2014 (Retro UNIX 8086 v1)
   258                              <1> 	;
   259                              <1> 	; 'sysret' first checks to see if process is about to be 
   260                              <1> 	; terminated (u.bsys). If it is, 'sysexit' is called.
   261                              <1> 	; If not, following happens:	 
   262                              <1> 	; 	1) The user's stack pointer is restored.
   263                              <1> 	;	2) r1=0 and 'iget' is called to see if last mentioned
   264                              <1> 	;	   i-node has been modified. If it has, it is written out
   265                              <1> 	;	   via 'ppoke'.
   266                              <1> 	;	3) If the super block has been modified, it is written out
   267                              <1> 	;	   via 'ppoke'.				
   268                              <1> 	;	4) If the dismountable file system's super block has been
   269                              <1> 	;	   modified, it is written out to the specified device
   270                              <1> 	;	   via 'ppoke'.
   271                              <1> 	;	5) A check is made if user's time quantum (uquant) ran out
   272                              <1> 	;	   during his execution. If so, 'tswap' is called to give
   273                              <1> 	;	   another user a chance to run.
   274                              <1> 	;	6) 'sysret' now goes into 'sysrele'. 
   275                              <1> 	;	    (See 'sysrele' for conclusion.)		
   276                              <1> 	;
   277                              <1> 	; Calling sequence:
   278                              <1> 	;	jump table or 'br sysret'
   279                              <1> 	; Arguments: 
   280                              <1> 	;	-	
   281                              <1> 	; ...............................................................
   282                              <1> 	;	
   283                              <1> 	; ((AX=r1 for 'iget' input))
   284                              <1> 	;	
   285 0000CF9A 31C0                <1> 	xor	eax, eax ; 28/02/2017
   286                              <1> sysret0: ; 29/07/2015 (eax = 0, jump from sysexec)
   287 0000CF9C FEC0                <1> 	inc	al ; 04/05/2013
   288 0000CF9E 3805[B2030300]      <1> 	cmp	[u.bsys], al ; 1
   289                              <1> 		; tstb u.bsys / is a process about to be terminated because
   290 0000CFA4 0F8377010000        <1>         jnb     sysexit ; 04/05/2013
   291                              <1> 		; bne sysexit / of an error? yes, go to sysexit
   292                              <1> 	;mov	esp, [u.usp] ; 24/05/2013 (that is not needed here)
   293                              <1> 		; mov u.sp,sp / no point stack to users stack
   294 0000CFAA FEC8                <1> 	dec 	al ; mov ax, 0
   295                              <1> 		; clr r1 / zero r1 to check last mentioned i-node
   296 0000CFAC E8FA2D0000          <1> 	call	iget
   297                              <1> 		; jsr r0,iget / if last mentioned i-node has been modified
   298                              <1> 		            ; / it is written out
   299                              <1> 	; 10/01/2017
   300                              <1> 	; 09/01/2017
   301                              <1> ;sysrele: ; < release >
   302                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   303                              <1> 	; 16/04/2015 - 14/10/2015 (Retro UNIX 386 v1)
   304                              <1> 	; 10/04/2013 - 07/03/2014 (Retro UNIX 8086 v1)
   305                              <1> 	;
   306                              <1> 	; 'sysrele' first calls 'tswap' if the time quantum for a user is
   307                              <1> 	;  zero (see 'sysret'). It then restores the user's registers and
   308                              <1> 	; turns off the system flag. It then checked to see if there is
   309                              <1> 	; an interrupt from the user by calling 'isintr'. If there is, 
   310                              <1> 	; the output gets flashed (see isintr) and interrupt action is
   311                              <1> 	; taken by a branch to 'intract'. If there is no interrupt from
   312                              <1> 	; the user, a rti is made.
   313                              <1> 	;
   314                              <1> 	; Calling sequence:
   315                              <1> 	;	Fall through a 'bne' in 'sysret' & ?
   316                              <1> 	; Arguments:
   317                              <1> 	;	-	
   318                              <1> 	; ...............................................................
   319                              <1> 	;	
   320                              <1> 	; 23/02/2014 (swapret)
   321                              <1> 	; 22/09/2013
   322                              <1> sysrel0: ;1:
   323 0000CFB1 803D[A8030300]00    <1> 	cmp	byte [u.quant], 0 ; 16/05/2013
   324                              <1> 		; tstb uquant / is the time quantum 0?
   325 0000CFB8 7705                <1>         ja      short swapret
   326                              <1> 		; bne 1f / no, don't swap it out
   327                              <1> sysrelease: ; 07/12/2013 (jump from 'clock')
   328 0000CFBA E8AF1B0000          <1> 	call	tswap
   329                              <1> 		; jsr r0,tswap / yes, swap it out
   330                              <1> 	
   331                              <1> ; Retro Unix 8086 v1 feature: return from 'swap' to 'swapret' address.
   332                              <1> swapret: ;1:
   333                              <1> 	; 10/09/2015
   334                              <1> 	; 01/09/2015
   335                              <1> 	; 14/05/2015
   336                              <1> 	; 16/04/2015 (Retro UNIX 386 v1 - 32 bit, pm modifications)
   337                              <1> 	; 26/05/2013 (Retro UNIX 8086 v1)
   338                              <1> 	; cli
   339                              <1> 	; 24/07/2015
   340                              <1> 	;
   341                              <1> 	;; 'esp' must be already equal to '[u.usp]' here ! 
   342                              <1> 	;; mov	esp, [u.usp]
   343                              <1> 
   344                              <1> 	; 22/09/2013
   345 0000CFBF E8E82D0000          <1> 	call	isintr
   346                              <1> 	; 20/10/2013
   347 0000CFC4 7405                <1> 	jz	short sysrel1
   348 0000CFC6 E83F010000          <1> 	call	intract
   349                              <1> 		; jsr r0,isintr / is there an interrupt from the user
   350                              <1> 		;     br intract / yes, output gets flushed, take interrupt
   351                              <1> 		               ; / action
   352                              <1> sysrel1:
   353 0000CFCB FA                  <1> 	cli	; 14/10/2015
   354                              <1> sysrel2:
   355                              <1> 	; 28/02/2017
   356                              <1> 	; Check if there is a (delayed) callback for current user/process
   357 0000CFCC A0[D7030300]        <1> 	mov	al, [u.irqwait]
   358 0000CFD1 240F                <1> 	and	al, 0Fh ; is there a waiting IRQ callback service ?
   359 0000CFD3 7444                <1> 	jz	short sysrel8 ; no
   360                              <1> 
   361                              <1> 	; Set return to IRQ callback service and return from the service
   362 0000CFD5 0FB6D8              <1> 	movzx	ebx, al
   363 0000CFD8 883D[D7030300]      <1> 	mov 	[u.irqwait], bh ; 0 ; reset
   364 0000CFDE 8A9B[FC1B0100]      <1> 	mov	bl, [ebx+IRQenum] ; (available) IRQ index +1 (1 to 9)
   365                              <1> 	; 01/03/2017
   366 0000CFE4 FECB                <1> 	dec	bl ; IRQ index number, 0 to 8
   367 0000CFE6 7831                <1> 	js	short sysrel8 ; 0 -> FFh (not in use!?) 
   368                              <1> 	;
   369 0000CFE8 A0[B3030300]        <1> 	mov 	al, [u.uno] ; current process (user) number 
   370 0000CFED 3883[B2700100]      <1> 	cmp	[ebx+IRQ.owner], al
   371 0000CFF3 7524                <1> 	jne	short sysrel8 ; it is not the current user/process !?
   372 0000CFF5 F683[C4700100]01    <1> 	test	byte [ebx+IRQ.method], 1 ; callback ?
   373 0000CFFC 741B                <1> 	jz	short sysrel8 ; not a callback method !?
   374                              <1> 
   375 0000CFFE 8B93[D6700100]      <1> 	mov	edx, [ebx+IRQ.addr] ; IRQ callback service address (virtual)
   376 0000D004 C605[D8030300]01    <1> 	mov	byte [u.r_lock], 1 ; IRQ callback service in progress flag
   377                              <1> 
   378 0000D00B E8061C0000          <1> 	call	wswap ; save user's registers & status 
   379                              <1> 		      ;	(for return from IRQ callback service)
   380                              <1> 
   381 0000D010 8B2D[5C030300]      <1> 	mov	ebp, [u.sp]; kernel's stack, points to EIP (user)
   382 0000D016 895500              <1> 	mov	[ebp], edx ; IRQ call back service address
   383                              <1> sysrel8:
   384 0000D019 FE0D[5B030300]      <1> 	dec	byte [sysflg]
   385                              <1> 		; decb sysflg / turn system flag off
   386                              <1> 	
   387 0000D01F A1[B8030300]        <1> 	mov	eax, [u.pgdir]	
   388 0000D024 0F22D8              <1> 	mov	cr3, eax  ; 1st PDE points to Kernel Page Table 0 (1st 4 MB)
   389                              <1> 			  ; (others are different than kernel page tables) 
   390                              <1> 	; 10/09/2015
   391 0000D027 61                  <1> 	popad ; edi, esi, ebp, temp (icrement esp by 4), ebx, edx, ecx, eax
   392                              <1> 		; mov (sp)+,sc / restore user registers
   393                              <1> 		; mov (sp)+,mq
   394                              <1> 		; mov (sp)+,ac
   395                              <1> 		; mov (sp)+,r5
   396                              <1> 		; mov (sp)+,r4
   397                              <1> 		; mov (sp)+,r3
   398                              <1> 		; mov (sp)+,r2
   399                              <1> 	;
   400 0000D028 A1[64030300]        <1> 	mov	eax, [u.r0]  ; ((return value in EAX))
   401 0000D02D 0FA9                <1> 	pop	gs
   402 0000D02F 0FA1                <1> 	pop	fs
   403 0000D031 07                  <1> 	pop	es
   404 0000D032 1F                  <1> 	pop	ds
   405                              <1> 	;or	word [esp+8], 200h ; 22/01/2017 ; force enabling interrupts
   406 0000D033 CF                  <1> 	iretd	
   407                              <1> 		; rti / no, return from interrupt
   408                              <1> 
   409                              <1> sysrele:
   410                              <1> 	; 24/03/2017
   411                              <1> 	; 28/02/2017
   412                              <1> 	; 27/02/2017
   413                              <1> 	; 29/01/2017
   414                              <1> 	; 14/01/2017
   415                              <1> 	; 13/01/2017
   416                              <1> 	; 09/01/2017, 10/01/2017, 12/01/2017
   417                              <1> 	; Major modification for TRDOS 386 (CallBack return)
   418                              <1> 	;
   419                              <1> 	; 'sysrele' system call restores previously saved
   420                              <1> 	; registers and addresses of the process
   421                              <1> 	; (Main purpose -in TRDOS 386- is to return from
   422                              <1> 	; timer callback service routine in ring 3 -user mode-.)
   423                              <1> 	;
   424                              <1> 	; check if the process is in timer callback phase
   425 0000D034 803D[D4030300]00    <1> 	cmp	byte [u.t_lock], 0 ; TIMER INT LOCK
   426                              <1> 	;je	short sysrel0 ; classic (Retro UNIX 386 type) sysrele
   427 0000D03B 7734                <1> 	ja	short sysrel3
   428                              <1> 	; 27/02/2017
   429 0000D03D 803D[D8030300]00    <1> 	cmp	byte [u.r_lock], 0 ; IRQ callback lock	
   430 0000D044 0F8667FFFFFF        <1> 	jna	sysrel0 ; classic sysrele ; 24/03/2017
   431 0000D04A E859000000          <1> 	call	sysrel7
   432 0000D04F 803D[D8030300]00    <1> 	cmp	byte [u.r_lock], 0 ; IRQ callback service lock
   433 0000D056 7628                <1> 	jna	short sysrel4
   434 0000D058 C605[D8030300]00    <1> 	mov	byte [u.r_lock], 0 ; reset
   435                              <1> 	;mov	byte [u.irqwait], 0 ; reset ; 28/02/2017
   436 0000D05F A0[D9030300]        <1> 	mov	al, [u.r_mode]
   437 0000D064 08C0                <1> 	or	al, al
   438 0000D066 7518                <1> 	jnz	short sysrel4
   439 0000D068 FEC8                <1> 	dec	al
   440 0000D06A A2[D9030300]        <1> 	mov	[u.r_mode], al ; 0FFh ; not necessary !?
   441 0000D06F EB32                <1> 	jmp	short sysrel6		
   442                              <1> sysrel3:
   443                              <1> 	; 27/02/2017
   444 0000D071 E832000000          <1> 	call	sysrel7
   445                              <1> 	; 14/01/2017
   446 0000D076 28C0                <1> 	sub	al, al
   447 0000D078 3805[D4030300]      <1> 	cmp	[u.t_lock], al ; 0 ; TIMER INT LOCK
   448 0000D07E 770E                <1> 	ja	short sysrel5 ; yes
   449                              <1> sysrel4:
   450                              <1> 	; 29/01/2017
   451 0000D080 8B44241C            <1> 	mov	eax, [esp+28] ; eax
   452 0000D084 A3[64030300]        <1> 	mov	[u.r0], eax
   453 0000D089 E93EFFFFFF          <1> 	jmp	sysrel2
   454                              <1> sysrel5:
   455 0000D08E A2[D4030300]        <1> 	mov	[u.t_lock], al ; 0 ; reset
   456 0000D093 A0[D5030300]        <1> 	mov	al, [u.t_mode]
   457 0000D098 20C0                <1> 	and	al, al
   458                              <1> 	;jnz	short sysrel2 ; 0FFh ; user mode
   459 0000D09A 75E4                <1> 	jnz	short sysrel4 ; 29/01/2017
   460 0000D09C FEC8                <1> 	dec	al
   461 0000D09E A2[D5030300]        <1> 	mov	[u.t_mode], al ; 0FFh ; not necessary !?
   462                              <1> sysrel6:
   463                              <1> 	; cpu will continue from the interrupted sytem call addr
   464 0000D0A3 61                  <1> 	popad		; edi, esi, ebp, esp, ebx, edx, ecx, eax
   465 0000D0A4 83C410              <1> 	add	esp, 16	; pass segment segisters: ds, es, fs, gs		
   466 0000D0A7 CF                  <1> 	iretd		; eip, cs, eflags
   467                              <1> 
   468                              <1> sysrel7:
   469 0000D0A8 0FB61D[B3030300]    <1> 	movzx	ebx, byte [u.uno] ; current process number
   470 0000D0AF 66C1E302            <1> 	shl	bx, 2
   471                              <1> 	;cmp	[ebx+p.tcb-4], eax ; 0 ; is there callback address ?
   472                              <1> 	;jna	short sysrel0 
   473                              <1> 	; yes, reset callback address then restore process registers 
   474                              <1> 	;mov	[ebx+p.tcb-4], eax ; 0 ; reset
   475 0000D0B3 8B83[BC000300]      <1> 	mov     eax, [ebx+p.upage-4] ; UPAGE address
   476 0000D0B9 FA                  <1> 	cli	; disable interrupts till 'iretd'
   477 0000D0BA E98F1B0000          <1> 	jmp	rswap ; restore process 'u' structure
   478                              <1>  
   479                              <1> badsys:
   480                              <1> 	; 25/12/2016
   481                              <1> 	; 18/04/2016 (TRDOS 386 = TRDOS v2.0)
   482                              <1> 	; 17/04/2011 (TRDOS v1.0, 'IFC.ASM')
   483                              <1> 	; 03/02/2011 ('trdos_ifc_routine')
   484                              <1> 	;
   485                              <1> 	; 16/04/2015 (Retro UNIX 386 v1, 'badsys')
   486                              <1> 	; (EIP, EAX values will be shown on screen with error message)
   487                              <1> 	; (EIP = 'CD 40h' instruction address -INT 40h-)
   488                              <1> 	; (EAX = Function number)  
   489                              <1> 	;
   490 0000D0BF FE05[B2030300]      <1> 	inc	byte [u.bsys]
   491                              <1> 	;
   492 0000D0C5 8B1D[5C030300]      <1> 	mov	ebx, [u.sp] ; esp at the beginning of 'sysent'
   493 0000D0CB 8B03                <1> 	mov	eax, [ebx] ; EIP (return address, not 'INT 30h' address)
   494 0000D0CD 83E802              <1> 	sub	eax, 2 ; CDh, ##h
   495 0000D0D0 E84B69FFFF          <1> 	call	dwordtohex
   496 0000D0D5 8915[D5190100]      <1> 	mov	[eip_str], edx
   497 0000D0DB A3[D9190100]        <1> 	mov	[eip_str+4], eax
   498 0000D0E0 A1[64030300]        <1> 	mov	eax, [u.r0]
   499 0000D0E5 E83669FFFF          <1> 	call	dwordtohex
   500 0000D0EA 8915[C4190100]      <1> 	mov	[eax_str], edx
   501 0000D0F0 A3[C8190100]        <1> 	mov	[eax_str+4], eax
   502                              <1> 
   503 0000D0F5 66C705[B9190100]34- <1> 	mov	word [int_num_str], SYSCALL_INT_NUM ; 25/12/2016
   503 0000D0FD 30                  <1>
   504                              <1> 
   505 0000D0FE BE[8B190100]        <1> 	mov	esi, ifc_msg ; "invalid funtion call !" msg (trdosk9.s)
   506 0000D103 E8FD9AFFFF          <1> 	call	print_msg
   507                              <1> 
   508 0000D108 EB17                <1> 	jmp	sysexit
   509                              <1> 
   510                              <1> intract: ; / interrupt action
   511                              <1> 	; 14/10/2015
   512                              <1> 	; 16/04/2015 (Retro UNIX 386 v1 - Beginning)
   513                              <1> 	; 09/05/2013 - 07/12/2013 (Retro UNIX 8086 v1)
   514                              <1> 	;
   515                              <1> 	; Retro UNIX 8086 v1 modification !
   516                              <1> 	; (Process/task switching and quit routine by using
   517                              <1> 	; Retro UNIX 8086 v1 keyboard interrupt output.))
   518                              <1> 	;
   519                              <1> 	; input -> 'u.quit'  (also value of 'u.intr' > 0)
   520                              <1> 	; output -> If value of 'u.quit' = FFFFh ('ctrl+brk' sign)
   521                              <1> 	;		'intract' will jump to 'sysexit'.
   522                              <1> 	;	    Intract will return to the caller 
   523                              <1> 	;		if value of 'u.quit' <> FFFFh. 	 
   524                              <1> 	; 14/10/2015
   525 0000D10A FB                  <1> 	sti
   526                              <1> 	; 07/12/2013	
   527 0000D10B 66FF05[AC030300]    <1> 	inc 	word [u.quit]
   528 0000D112 7408                <1> 	jz	short intrct0 ; FFFFh -> 0
   529 0000D114 66FF0D[AC030300]    <1> 	dec	word [u.quit]
   530                              <1> 	; 16/04/2015
   531 0000D11B C3                  <1> 	retn
   532                              <1> intrct0:	
   533 0000D11C 58                  <1> 	pop	eax ; call intract -> retn
   534                              <1> 	;
   535 0000D11D 31C0                <1> 	xor 	eax, eax
   536 0000D11F FEC0                <1> 	inc	al  ; mov ax, 1
   537                              <1> ;;;
   538                              <1> 	; UNIX v1 original 'intract' routine... 
   539                              <1> 	; / interrupt action
   540                              <1> 		;cmp *(sp),$rti / are you in a clock interrupt?
   541                              <1> 		; bne 1f / no, 1f
   542                              <1> 		; cmp (sp)+,(sp)+ / pop clock pointer
   543                              <1> 	; 1: / now in user area
   544                              <1> 		; mov r1,-(sp) / save r1
   545                              <1> 		; mov u.ttyp,r1 
   546                              <1> 			; / pointer to tty buffer in control-to r1
   547                              <1> 		; cmpb 6(r1),$177
   548                              <1> 			; / is the interrupt char equal to "del"
   549                              <1> 		; beq 1f / yes, 1f
   550                              <1> 		; clrb 6(r1) 
   551                              <1> 		        ; / no, clear the byte 
   552                              <1> 			; / (must be a quit character)
   553                              <1> 		; mov (sp)+,r1 / restore r1
   554                              <1> 		; clr u.quit / clear quit flag
   555                              <1> 		; bis $20,2(sp) 
   556                              <1> 		    	; / set trace for quit (sets t bit of 
   557                              <1> 			; / ps-trace trap)
   558                              <1> 		; rti   ;  / return from interrupt
   559                              <1> 	; 1: / interrupt char = del
   560                              <1> 		; clrb 6(r1) / clear the interrupt byte 
   561                              <1> 			   ; / in the buffer
   562                              <1> 		; mov (sp)+,r1 / restore r1
   563                              <1> 		; cmp u.intr,$core / should control be 
   564                              <1> 				; / transferred to loc core?
   565                              <1> 		; blo 1f
   566                              <1> 		; jmp *u.intr / user to do rti yes, 
   567                              <1> 				; / transfer to loc core
   568                              <1> 	; 1:
   569                              <1> 		; sys 1 / exit
   570                              <1> 
   571                              <1> sysexit: ; <terminate process>
   572                              <1> 	; 14/11/2017
   573                              <1> 	; 27/05/2017
   574                              <1> 	; 10/04/2017
   575                              <1> 	; 26/02/2017, 28/02/2017
   576                              <1> 	; 02/01/2017, 23/01/2017
   577                              <1> 	; 06/06/2016, 10/06/2016
   578                              <1> 	; 19/05/2016, 23/05/2016
   579                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   580                              <1> 	; 16/04/2015 - 01/09/2015 (Retro UNIX 386 v1)
   581                              <1> 	; 19/04/2013 - 14/02/2014 (Retro UNIX 8086 v1)
   582                              <1> 	;
   583                              <1> 	; 'sysexit' terminates a process. First each file that
   584                              <1> 	; the process has opened is closed by 'flose'. The process
   585                              <1> 	; status is then set to unused. The 'p.pid' table is then
   586                              <1> 	; searched to find children of the dying process. If any of
   587                              <1> 	; children are zombies (died by not waited for), they are
   588                              <1> 	; set free. The 'p.pid' table is then searched to find the
   589                              <1> 	; dying process's parent. When the parent is found, it is
   590                              <1> 	; checked to see if it is free or it is a zombie. If it is
   591                              <1> 	; one of these, the dying process just dies. If it is waiting
   592                              <1> 	; for a child process to die, it notified that it doesn't 
   593                              <1> 	; have to wait anymore by setting it's status from 2 to 1
   594                              <1> 	; (waiting to active). It is awakened and put on runq by
   595                              <1> 	; 'putlu'. The dying process enters a zombie state in which
   596                              <1> 	; it will never be run again but stays around until a 'wait'
   597                              <1> 	; is completed by it's parent process. If the parent is not
   598                              <1> 	; found, process just dies. This means 'swap' is called with
   599                              <1> 	; 'u.uno=0'. What this does is the 'wswap' is not called
   600                              <1> 	; to write out the process and 'rswap' reads the new process
   601                              <1> 	; over the one that dies..i.e., the dying process is 
   602                              <1> 	; overwritten and destroyed.	
   603                              <1>  	;
   604                              <1> 	; Calling sequence:
   605                              <1> 	;	sysexit or conditional branch.
   606                              <1> 	; Arguments:
   607                              <1> 	;	-	
   608                              <1> 	; ...............................................................
   609                              <1> 	;	
   610                              <1> 	; Retro UNIX 8086 v1 modification: 
   611                              <1> 	;       System call number (=1) is in EAX register.
   612                              <1> 	;
   613                              <1> 	;       Other parameters are in EDX, EBX, ECX, ESI, EDI, EBP
   614                              <1> 	;       registers depending of function details.
   615                              <1> 	;
   616                              <1> 	; ('swap' procedure is mostly different than original UNIX v1.)
   617                              <1> 	;
   618                              <1> ; / terminate process
   619                              <1> 	; AX = 1
   620 0000D121 6648                <1> 	dec 	ax ; 0
   621 0000D123 66A3[AA030300]      <1> 	mov	[u.intr], ax ; 0
   622                              <1> 		; clr u.intr / clear interrupt control word
   623                              <1> 		; clr r1 / clear r1
   624                              <1> sysexit_0:
   625                              <1> 	; 23/01/2017
   626                              <1> 	; 02/01/2017
   627                              <1> 	; 10/06/2016
   628                              <1> 	; 06/06/2016
   629                              <1> 	; 23/05/2016
   630                              <1> 	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
   631                              <1> 	; Check and stop/clear timer event(s) of this (dying) process
   632                              <1> 	; if there is.
   633                              <1> 
   634                              <1> 	; 02/01/2017 
   635 0000D129 FA                  <1> 	cli	; disable interrupts
   636                              <1> 	; 23/01/2017 - reset timer frequency (to 18.2Hz)
   637 0000D12A B036                <1> 	mov	al, 00110110b ; 36h
   638 0000D12C E643                <1>  	out	43h, al
   639 0000D12E 28C0                <1> 	sub	al, al ; 0
   640 0000D130 E640                <1> 	out	40h, al ; LB
   641 0000D132 E640                <1> 	out	40h, al ; HB
   642                              <1>  	; 
   643 0000D134 0FB61D[B3030300]    <1> 	movzx	ebx, byte [u.uno]
   644                              <1> 	;mov	bl, [u.uno] ; process number of dying process
   645 0000D13B 3883[FF000300]      <1> 	cmp	byte [ebx+p.timer-1], al ; 0
   646 0000D141 763A                <1> 	jna	short sysexit_12 ; no timer events for this process
   647 0000D143 8883[FF000300]      <1> 	mov	byte [ebx+p.timer-1], al ; 0 ; reset
   648                              <1> 	;mov	al, [timer_events]
   649                              <1> 	;or	al, al
   650                              <1>  	;jz	short sysexit_12 ; no timer events
   651                              <1> 	;mov	cl, al
   652 0000D149 8A0D[136B0100]      <1> 	mov	cl, [timer_events] ; 14/11/2017
   653                              <1> 	;cli	; disable interrupts 
   654 0000D14F B410                <1> 	mov	ah, 16 ; number of available timer events
   655 0000D151 BE[60040300]        <1> 	mov	esi, timer_set ; beginning address of timer events
   656                              <1> sysexit_7:
   657 0000D156 8A06                <1> 	mov	al, [esi] ; process number (of timer event)
   658 0000D158 38D8                <1> 	cmp	al, bl ; process number comparison
   659 0000D15A 7411                <1> 	je	short sysexit_10
   660 0000D15C 20C0                <1> 	and	al, al
   661 0000D15E 7404                <1> 	jz	short sysexit_9
   662                              <1> sysexit_8:
   663 0000D160 FEC9                <1> 	dec	cl
   664 0000D162 7416                <1> 	jz	short sysexit_11
   665                              <1> sysexit_9:
   666 0000D164 FECC                <1> 	dec	ah
   667 0000D166 7415                <1> 	jz	short sysexit_12
   668 0000D168 83C610              <1> 	add	esi, 16
   669 0000D16B EBE9                <1> 	jmp	short sysexit_7
   670                              <1> 
   671                              <1> sysexit_10:
   672                              <1> 	;mov	byte [esi], 0
   673 0000D16D 66C7060000          <1> 	mov	word [esi], 0
   674                              <1> 	;mov	dword [esi+12], 0
   675                              <1> 	;
   676 0000D172 FE0D[136B0100]      <1> 	dec	byte [timer_events] ; 02/01/2017
   677                              <1> 	;
   678 0000D178 EBE6                <1> 	jmp	short sysexit_8
   679                              <1> 
   680                              <1> sysexit_11:
   681 0000D17A 6629C0              <1> 	sub	ax, ax ; 0 ; 26/02/2017
   682                              <1> sysexit_12:
   683                              <1> 	; 26/02/2017 (Unlink IRQ callbacks belong to the user)
   684 0000D17D 803D[D6030300]00    <1> 	cmp	byte [u.irqc], 0 ; Count of IRQ callbacks
   685 0000D184 7E2E                <1> 	jng	short sysexit_16 ; zero or invalid
   686                              <1> 	; 28/02/2017
   687                              <1> 	; clear IRQ callback flags (for 'sysrele' and 'sysret')
   688 0000D186 A2[D7030300]        <1> 	mov	[u.irqwait], al ; 0 ; force to clear waiting flag
   689 0000D18B A2[D8030300]        <1> 	mov	[u.r_lock], al ; 0 ; force to clear busy flag
   690 0000D190 BE[B2700100]        <1> 	mov	esi, IRQ.owner
   691                              <1> sysexit_13:	
   692 0000D195 AC                  <1> 	lodsb
   693 0000D196 3A05[B3030300]      <1> 	cmp	al, [u.uno] ; owner  = current user ?
   694 0000D19C 750C                <1> 	jne	short sysexit_14
   695 0000D19E C646FF00            <1> 	mov	byte [esi-1], 0 ; owner = 0 : Free
   696 0000D1A2 FE0D[D6030300]      <1> 	dec	byte [u.irqc]
   697 0000D1A8 7408                <1> 	jz	short sysexit_15
   698                              <1> sysexit_14:
   699 0000D1AA 81FE[BA700100]      <1> 	cmp	esi, IRQ.owner + 8 ; the last IRQ index number ?
   700 0000D1B0 76E3                <1> 	jna	short sysexit_13 ; no
   701                              <1> sysexit_15:
   702 0000D1B2 30C0                <1> 	xor	al, al ; 0
   703                              <1> sysexit_16: ; 2:
   704 0000D1B4 FB                  <1> 	sti	; enable interrupts 
   705                              <1> 	;
   706                              <1> 	; AX = 0
   707                              <1> sysexit_1: ; 1:
   708                              <1> 	; AX = File descriptor
   709                              <1> 		; / r1 has file descriptor (index to u.fp list)
   710                              <1> 		; / Search the whole list
   711 0000D1B5 E8C7100000          <1> 	call	fclose
   712                              <1> 		; jsr r0,fclose / close all files the process opened
   713                              <1> 	;; ignore error return
   714                              <1> 		; br .+2 / ignore error return
   715                              <1> 	;inc	ax
   716 0000D1BA FEC0                <1> 	inc	al
   717                              <1> 		; inc r1 / increment file descriptor
   718                              <1> 	;cmp	ax, 10
   719 0000D1BC 3C0A                <1> 	cmp	al, 10
   720                              <1> 		; cmp r1,$10. / end of u.fp list?
   721 0000D1BE 72F5                <1> 	jb	short sysexit_1
   722                              <1> 		; blt 1b / no, go back
   723                              <1> 	;movzx	ebx, byte [u.uno]
   724 0000D1C0 8A1D[B3030300]      <1> 	mov	bl, [u.uno] ; 02/01/2017
   725                              <1> 		; movb	u.uno,r1 / yes, move dying process's number to r1
   726 0000D1C6 88A3[AF000300]      <1> 	mov	[ebx+p.stat-1], ah ; 0, SFREE
   727                              <1> 		; clrb p.stat-1(r1) / free the process
   728                              <1> 	; 10/04/2017
   729 0000D1CC 381D[29710100]      <1> 	cmp	[audio_user], bl
   730 0000D1D2 7518                <1> 	jne	short sysexit_17
   731                              <1> 	; reset audio device (current) owner and 'initializated' flag
   732 0000D1D4 883D[29710100]      <1> 	mov	[audio_user], bh ; 0
   733                              <1> 	; 27/05/2017
   734 0000D1DA 8B0D[14710100]      <1> 	mov	ecx,  [audio_buffer]
   735 0000D1E0 09C9                <1> 	or	ecx, ecx
   736 0000D1E2 7408                <1> 	jz	short sysexit_17
   737                              <1> 	; 'deallocate_user_pages' is not necessary in sysexit !!!
   738                              <1> 	;push	ebx
   739                              <1> 	;mov	ebx, ecx
   740                              <1> 	;mov	ecx, [audio_buff_size]
   741                              <1> 	;call	deallocate_user_pages
   742                              <1> 	;; (Modified Registers -> EAX, EDX, ESI, EDI, EBX, ECX, EBP)
   743 0000D1E4 29C9                <1> 	sub	ecx, ecx
   744 0000D1E6 890D[14710100]      <1> 	mov	[audio_buffer], ecx ; 0
   745                              <1> 	;pop	ebx
   746                              <1> sysexit_17:
   747                              <1> 	;shl	bx, 1
   748 0000D1EC D0E3                <1> 	shl	bl, 1
   749                              <1> 		; asl r1 / use r1 for index into the below tables
   750 0000D1EE 668B8B[1E000300]    <1> 	mov	cx, [ebx+p.pid-2]
   751                              <1> 		; mov p.pid-2(r1),r3 / move dying process's name to r3
   752 0000D1F5 668B93[3E000300]    <1> 	mov	dx, [ebx+p.ppid-2]
   753                              <1> 		; mov p.ppid-2(r1),r4 / move its parents name to r4
   754                              <1> 	; xor 	bx, bx ; 0
   755 0000D1FC 30DB                <1> 	xor	bl, bl ; 0
   756                              <1> 		; clr r2
   757 0000D1FE 31F6                <1> 	xor	esi, esi ; 0
   758                              <1> 		; clr r5 / initialize reg
   759                              <1> sysexit_2: ; 1:
   760                              <1> 	        ; / find children of this dying process, 
   761                              <1> 		; / if they are zombies, free them
   762                              <1> 	;add	bx, 2
   763 0000D200 80C302              <1> 	add	bl, 2
   764                              <1> 		; add $2,r2 / search parent process table 
   765                              <1> 		          ; / for dying process's name
   766 0000D203 66398B[3E000300]    <1> 	cmp	[ebx+p.ppid-2], cx
   767                              <1> 		; cmp p.ppid-2(r2),r3 / found it?
   768 0000D20A 7513                <1> 	jne	short sysexit_4
   769                              <1> 		; bne 3f / no
   770                              <1> 	;shr	bx, 1
   771 0000D20C D0EB                <1> 	shr	bl, 1
   772                              <1> 		; asr r2 / yes, it is a parent
   773 0000D20E 80BB[AF000300]03    <1> 	cmp	byte [ebx+p.stat-1], 3 ; SZOMB
   774                              <1> 		; cmpb p.stat-1(r2),$3 / is the child of this 
   775                              <1> 				     ; / dying process a zombie
   776 0000D215 7506                <1> 	jne	short sysexit_3 
   777                              <1> 		; bne 2f / no
   778 0000D217 88A3[AF000300]      <1> 	mov	[ebx+p.stat-1], ah ; 0, SFREE
   779                              <1> 		; clrb p.stat-1(r2) / yes, free the child process
   780                              <1> sysexit_3: ; 2:
   781                              <1> 	;shr	bx, 1
   782 0000D21D D0E3                <1> 	shl	bl, 1
   783                              <1> 		; asl r2
   784                              <1> sysexit_4: ; 3:
   785                              <1> 		; / search the process name table 
   786                              <1> 		; / for the dying process's parent
   787 0000D21F 663993[1E000300]    <1> 	cmp	[ebx+p.pid-2], dx
   788                              <1> 		; cmp p.pid-2(r2),r4 / found it?
   789 0000D226 7502                <1> 	jne	short sysexit_5
   790                              <1> 		; bne 3f / no
   791 0000D228 89DE                <1> 	mov	esi, ebx
   792                              <1> 		; mov r2,r5 / yes, put index to p.pid table (parents
   793                              <1> 		          ; / process # x2) in r5
   794                              <1> sysexit_5: ; 3:
   795                              <1> 	;cmp	bx, nproc + nproc
   796 0000D22A 80FB20              <1> 	cmp	bl, nproc + nproc
   797                              <1> 		; cmp r2,$nproc+nproc / has whole table been searched?
   798 0000D22D 72D1                <1> 	jb	short sysexit_2
   799                              <1> 		; blt 1b / no, go back
   800                              <1> 		; mov r5,r1 / yes, r1 now has parents process # x2
   801 0000D22F 21F6                <1> 	and	esi, esi ; r5=r1
   802 0000D231 7436                <1> 	jz	short sysexit_6
   803                              <1> 		; beq 2f / no parent has been found. 
   804                              <1> 		       ; / The process just dies
   805 0000D233 66D1EE              <1> 	shr	si, 1
   806                              <1> 		; asr r1 / set up index to p.stat
   807 0000D236 8A86[AF000300]      <1> 	mov	al, [esi+p.stat-1]
   808                              <1> 		; movb p.stat-1(r1),r2 / move status of parent to r2
   809 0000D23C 20C0                <1> 	and	al, al
   810 0000D23E 7429                <1> 	jz	short sysexit_6
   811                              <1> 		; beq 2f / if its been freed, 2f
   812 0000D240 3C03                <1> 	cmp	al, 3
   813                              <1> 		; cmp r2,$3 / is parent a zombie?
   814 0000D242 7425                <1> 	je	short sysexit_6
   815                              <1> 		; beq 2f / yes, 2f
   816                              <1> 	; BH = 0
   817 0000D244 8A1D[B3030300]      <1> 	mov	bl, [u.uno]
   818                              <1> 		; movb u.uno,r3 / move dying process's number to r3
   819 0000D24A C683[AF000300]03    <1> 	mov	byte [ebx+p.stat-1], 3  ; SZOMB
   820                              <1> 		; movb $3,p.stat-1(r3) / make the process a zombie
   821 0000D251 3C01                <1> 	cmp	al, 1 ; SRUN
   822 0000D253 7414                <1> 	je	short sysexit_6
   823                              <1> 	;cmp	al, 2
   824                              <1> 		; cmp r2,$2 / is the parent waiting for 
   825                              <1> 			  ; / this child to die
   826                              <1> 	;jne	short sysexit_6	
   827                              <1> 		; bne 2f / yes, notify parent not to wait any more
   828                              <1> 	; p.stat = 2 --> waiting
   829                              <1> 	; p.stat = 4 --> sleeping
   830 0000D255 C686[AF000300]01    <1> 	mov	byte [esi+p.stat-1], 1 ; SRUN
   831                              <1> 	;dec	byte [esi+p.stat-1]
   832                              <1> 		; decb	p.stat-1(r1) / awaken it by putting it (parent)
   833 0000D25C 6689F0              <1> 	mov	ax, si ; r1  (process number in AL)
   834                              <1> 	; 
   835                              <1> 	;mov	ebx, runq + 4
   836                              <1> 		; mov $runq+4,r2 / on the runq
   837 0000D25F BB[54030300]        <1> 	mov	ebx, runq+2 ; normal run queue ; 02/01/2017
   838 0000D264 E81D1A0000          <1> 	call	putlu
   839                              <1> 		; jsr r0, putlu
   840                              <1> sysexit_6: 
   841                              <1> 		; / the process dies
   842 0000D269 C605[B3030300]00    <1> 	mov	byte [u.uno], 0
   843                              <1> 		; clrb u.uno / put zero as the process number, 
   844                              <1> 	           ; / so "swap" will
   845 0000D270 E813190000          <1> 	call	swap
   846                              <1> 		; jsr r0,swap / overwrite process with another process
   847                              <1> 
   848                              <1> hlt_sys:
   849                              <1> 	;sti
   850                              <1> hlts0:
   851 0000D275 F4                  <1> 	hlt
   852 0000D276 EBFD                <1> 	jmp	short hlts0
   853                              <1> 		; 0 / and thereby kill it; halt?
   854                              <1> 
   855                              <1> syswait: ; < wait for a processs to die >
   856                              <1> 	; 17/09/2015
   857                              <1> 	; 02/09/2015
   858                              <1> 	; 01/09/2015
   859                              <1> 	; 16/04/2015 (Retro UNIX 386 v1 - Beginning)
   860                              <1> 	; 24/05/2013 - 05/02/2014 (Retro UNIX 8086 v1)
   861                              <1> 	;
   862                              <1> 	; 'syswait' waits for a process die. 
   863                              <1> 	; It works in following way:
   864                              <1> 	;    1) From the parent process number, the parent's 
   865                              <1> 	; 	process name is found. The p.ppid table of parent
   866                              <1> 	;	names is then searched for this process name.
   867                              <1> 	;	If a match occurs, r2 contains child's process
   868                              <1> 	;	number. The child status is checked to see if it is
   869                              <1> 	;	a zombie, i.e; dead but not waited for (p.stat=3)
   870                              <1> 	;	If it is, the child process is freed and it's name
   871                              <1> 	;	is put in (u.r0). A return is then made via 'sysret'.
   872                              <1> 	;	If the child is not a zombie, nothing happens and
   873                              <1> 	;	the search goes on through the p.ppid table until
   874                              <1> 	;	all processes are checked or a zombie is found.
   875                              <1> 	;    2) If no zombies are found, a check is made to see if
   876                              <1> 	;	there are any children at all. If there are none,
   877                              <1> 	;	an error return is made. If there are, the parent's
   878                              <1> 	;	status is set to 2 (waiting for child to die),
   879                              <1> 	;	the parent is swapped out, and a branch to 'syswait'
   880                              <1> 	;	is made to wait on the next process.
   881                              <1> 	;
   882                              <1> 	; Calling sequence:
   883                              <1> 	;	?
   884                              <1> 	; Arguments:
   885                              <1> 	;	-
   886                              <1> 	; Inputs: - 
   887                              <1> 	; Outputs: if zombie found, it's name put in u.r0.	
   888                              <1> 	; ...............................................................
   889                              <1> 	;				
   890                              <1> 	
   891                              <1> ; / wait for a process to die
   892                              <1> 
   893                              <1> syswait_0:
   894 0000D278 0FB61D[B3030300]    <1> 	movzx	ebx, byte [u.uno] ; 01/09/2015
   895                              <1> 		; movb u.uno,r1 / put parents process number in r1
   896 0000D27F D0E3                <1> 	shl	bl, 1
   897                              <1> 	;shl	bx, 1
   898                              <1> 		; asl r1 / x2 to get index into p.pid table
   899 0000D281 668B83[1E000300]    <1> 	mov	ax, [ebx+p.pid-2]
   900                              <1> 		; mov p.pid-2(r1),r1 / get the name of this process
   901 0000D288 31F6                <1> 	xor	esi, esi
   902                              <1> 		; clr r2
   903 0000D28A 31C9                <1> 	xor	ecx, ecx ; 30/10/2013
   904                              <1> 	;xor 	cl, cl
   905                              <1> 		; clr r3 / initialize reg 3
   906                              <1> syswait_1: ; 1:
   907 0000D28C 6683C602            <1> 	add	si, 2
   908                              <1> 		; add $2,r2 / use r2 for index into p.ppid table
   909                              <1> 			  ; / search table of parent processes 
   910                              <1> 			  ; / for this process name
   911 0000D290 663B86[3E000300]    <1> 	cmp	ax, [esi+p.ppid-2]
   912                              <1> 		; cmp p.ppid-2(r2),r1 / r2 will contain the childs 
   913                              <1> 			            ; / process number
   914 0000D297 7535                <1> 	jne	short syswait_3
   915                              <1> 		;bne 3f / branch if no match of parent process name
   916                              <1> 	;inc	cx
   917 0000D299 FEC1                <1> 	inc	cl
   918                              <1> 		;inc r3 / yes, a match, r3 indicates number of children
   919 0000D29B 66D1EE              <1> 	shr	si, 1
   920                              <1> 		; asr r2 / r2/2 to get index to p.stat table
   921                              <1> 	; The possible states ('p.stat' values) of a process are:
   922                              <1> 	;	0 = free or unused
   923                              <1> 	;	1 = active
   924                              <1> 	;	2 = waiting for a child process to die
   925                              <1> 	;	3 = terminated, but not yet waited for (zombie).	
   926 0000D29E 80BE[AF000300]03    <1> 	cmp	byte [esi+p.stat-1], 3 ; SZOMB, 05/02/2014
   927                              <1> 		; cmpb p.stat-1(r2),$3 / is the child process a zombie?
   928 0000D2A5 7524                <1> 	jne	short syswait_2
   929                              <1> 		; bne 2f / no, skip it
   930 0000D2A7 88BE[AF000300]      <1> 	mov	[esi+p.stat-1], bh ; 0
   931                              <1> 		; clrb p.stat-1(r2) / yes, free it
   932 0000D2AD 66D1E6              <1> 	shl	si, 1
   933                              <1> 		; asl r2 / r2x2 to get index into p.pid table
   934 0000D2B0 0FB786[1E000300]    <1> 	movzx	eax, word [esi+p.pid-2]
   935 0000D2B7 A3[64030300]        <1> 	mov	[u.r0], eax
   936                              <1> 		; mov p.pid-2(r2),*u.r0 
   937                              <1> 			      ; / put childs process name in (u.r0)
   938                              <1> 	;
   939                              <1> 	; Retro UNIX 386 v1 modification ! (17/09/2015)
   940                              <1> 	;
   941                              <1> 	; Parent process ID -p.ppid- field (of the child process)
   942                              <1> 	; must be cleared in order to prevent infinitive 'syswait'
   943                              <1> 	; system call loop from the application/program if it calls
   944                              <1> 	; 'syswait' again (mistakenly) while there is not a zombie
   945                              <1> 	; or running child process to wait. ('forktest.s', 17/09/2015)
   946                              <1> 	;
   947                              <1> 	; Note: syswait will return with error if there is not a
   948                              <1> 	;       zombie or running process to wait.	
   949                              <1> 	;
   950 0000D2BC 6629C0              <1> 	sub	ax, ax
   951 0000D2BF 668986[3E000300]    <1> 	mov 	[esi+p.ppid-2], ax ; 0 ; 17/09/2015
   952 0000D2C6 E9D1FCFFFF          <1> 	jmp	sysret0 ; ax = 0
   953                              <1> 	;
   954                              <1> 	;jmp	sysret
   955                              <1> 		; br sysret1 / return cause child is dead
   956                              <1> syswait_2: ; 2:
   957 0000D2CB 66D1E6              <1> 	shl	si, 1
   958                              <1> 		; asl r2 / r2x2 to get index into p.ppid table
   959                              <1> syswait_3: ; 3:
   960 0000D2CE 6683FE20            <1> 	cmp	si, nproc+nproc
   961                              <1> 		; cmp r2,$nproc+nproc / have all processes been checked?
   962 0000D2D2 72B8                <1> 	jb	short syswait_1
   963                              <1> 		; blt 1b / no, continue search
   964                              <1> 	;and	cx, cx
   965 0000D2D4 20C9                <1> 	and	cl, cl
   966                              <1> 		; tst r3 / one gets here if there are no children 
   967                              <1> 		       ; / or children that are still active
   968                              <1> 	; 30/10/2013
   969 0000D2D6 750B                <1> 	jnz	short syswait_4
   970                              <1> 	;jz	error
   971                              <1> 		; beq error1 / there are no children, error
   972 0000D2D8 890D[64030300]      <1> 	mov	[u.r0], ecx ; 0
   973 0000D2DE E997FCFFFF          <1> 	jmp	error
   974                              <1> syswait_4:
   975 0000D2E3 8A1D[B3030300]      <1> 	mov	bl, [u.uno]
   976                              <1> 		; movb u.uno,r1 / there are children so put 
   977                              <1> 			      ; / parent process number in r1
   978 0000D2E9 FE83[AF000300]      <1> 	inc	byte [ebx+p.stat-1] ; 2, SWAIT, 05/02/2014
   979                              <1> 		; incb p.stat-1(r1) / it is waiting for 
   980                              <1> 				  ; / other children to die
   981                              <1> 	; 04/11/2013
   982 0000D2EF E894180000          <1> 	call	swap
   983                              <1> 		; jsr r0,swap / swap it out, because it's waiting
   984 0000D2F4 EB82                <1> 	jmp	syswait_0
   985                              <1> 		; br syswait / wait on next process
   986                              <1> 
   987                              <1> sysfork: ; < create a new process >
   988                              <1> 	; 02/01/2017 (TRDOS 386 modification)
   989                              <1> 	; 04/09/2015, 18/05/2015
   990                              <1> 	; 28/08/2015, 01/09/2015, 02/09/2015
   991                              <1> 	; 09/05/2015, 10/05/2015, 14/05/2015
   992                              <1> 	; 06/05/2015 (Retro UNIX 386 v1 - Beginning)
   993                              <1> 	; 24/05/2013 - 14/02/2014 (Retro UNIX 8086 v1)
   994                              <1> 	;
   995                              <1> 	; 'sysfork' creates a new process. This process is referred
   996                              <1> 	; to as the child process. This new process core image is
   997                              <1> 	; a copy of that of the caller of 'sysfork'. The only
   998                              <1> 	; distinction is the return location and the fact that (u.r0)
   999                              <1> 	; in the old process (parent) contains the process id (p.pid)
  1000                              <1> 	; of the new process (child). This id is used by 'syswait'.
  1001                              <1> 	; 'sysfork' works in the following manner: 	
  1002                              <1> 	;    1) The process status table (p.stat) is searched to find
  1003                              <1> 	;	a process number that is unused. If none are found
  1004                              <1> 	;	an error occurs.
  1005                              <1> 	;    2) when one is found, it becomes the child process number
  1006                              <1> 	;	and it's status (p.stat) is set to active.
  1007                              <1> 	;    3) If the parent had a control tty, the interrupt 
  1008                              <1> 	;	character in that tty buffer is cleared.
  1009                              <1> 	;    4) The child process is put on the lowest priority run 
  1010                              <1> 	;	queue via 'putlu'.
  1011                              <1> 	;    5) A new process name is gotten from 'mpid' (actually 
  1012                              <1> 	;	it is a unique number) and is put in the child's unique
  1013                              <1> 	;	identifier; process id (p.pid).
  1014                              <1> 	;    6) The process name of the parent is then obtained and
  1015                              <1> 	;	placed in the unique identifier of the parent process
  1016                              <1> 	;	name is then put in 'u.r0'.	
  1017                              <1> 	;    7) The child process is then written out on disk by
  1018                              <1> 	;	'wswap',i.e., the parent process is copied onto disk
  1019                              <1> 	;	and the child is born. (The child process is written 
  1020                              <1> 	;	out on disk/drum with 'u.uno' being the child process
  1021                              <1> 	;	number.)
  1022                              <1> 	;    8) The parent process number is then restored to 'u.uno'.
  1023                              <1> 	;    9) The child process name is put in 'u.r0'.
  1024                              <1> 	;   10) The pc on the stack sp + 18 is incremented by 2 to
  1025                              <1> 	;	create the return address for the parent process.
  1026                              <1> 	;   11) The 'u.fp' list as then searched to see what files
  1027                              <1> 	;	the parent has opened. For each file the parent has
  1028                              <1> 	;	opened, the corresponding 'fsp' entry must be updated
  1029                              <1> 	;	to indicate that the child process also has opened
  1030                              <1> 	;	the file. A branch to 'sysret' is then made.	 			 				
  1031                              <1> 	;
  1032                              <1> 	; Calling sequence:
  1033                              <1> 	;	from shell ?
  1034                              <1> 	; Arguments:
  1035                              <1> 	;	-
  1036                              <1> 	; Inputs: -
  1037                              <1> 	; Outputs: *u.r0 - child process name
  1038                              <1> 	; ...............................................................
  1039                              <1> 	;	
  1040                              <1> 	; Retro UNIX 8086 v1 modification: 
  1041                              <1> 	;	AX = r0 = PID (>0) (at the return of 'sysfork')
  1042                              <1> 	;	= process id of child a parent process returns
  1043                              <1> 	;	= process id of parent when a child process returns
  1044                              <1> 	;
  1045                              <1> 	;       In original UNIX v1, sysfork is called and returns as
  1046                              <1> 	;	in following manner: (with an example: c library, fork)
  1047                              <1> 	;	
  1048                              <1> 	;	1:
  1049                              <1> 	;		sys	fork
  1050                              <1> 	;			br 1f  / child process returns here
  1051                              <1> 	;		bes	2f     / parent process returns here
  1052                              <1> 	;		/ pid of new process in r0
  1053                              <1> 	;		rts	pc
  1054                              <1> 	;	2: / parent process condionally branches here
  1055                              <1> 	;		mov	$-1,r0 / pid = -1 means error return
  1056                              <1> 	;		rts	pc
  1057                              <1> 	;
  1058                              <1> 	;	1: / child process brances here
  1059                              <1> 	;		clr	r0   / pid = 0 in child process
  1060                              <1> 	;		rts	pc
  1061                              <1> 	;
  1062                              <1> 	;	In UNIX v7x86 (386) by Robert Nordier (1999)
  1063                              <1> 	;		// pid = fork();
  1064                              <1> 	;		//
  1065                              <1> 	;		// pid == 0 in child process; 
  1066                              <1> 	;		// pid == -1 means error return
  1067                              <1> 	;		// in child, 
  1068                              <1> 	;		//	parents id is in par_uid if needed
  1069                              <1> 	;		
  1070                              <1> 	;		_fork:
  1071                              <1> 	;			mov	$.fork,eax
  1072                              <1> 	;			int	$0x30
  1073                              <1> 	;			jmp	1f
  1074                              <1> 	;			jnc	2f
  1075                              <1> 	;			jmp	cerror
  1076                              <1> 	;		1:
  1077                              <1> 	;			mov	eax,_par_uid
  1078                              <1> 	;			xor	eax,eax
  1079                              <1> 	;		2:
  1080                              <1> 	;			ret
  1081                              <1> 	;
  1082                              <1> 	;	In Retro UNIX 8086 v1,
  1083                              <1> 	;	'sysfork' returns in following manner:
  1084                              <1> 	;	
  1085                              <1> 	;		mov	ax, sys_fork
  1086                              <1> 	;		mov	bx, offset @f ; routine for child
  1087                              <1> 	;		int	20h
  1088                              <1> 	;		jc	error
  1089                              <1> 	;		
  1090                              <1> 	;	; Routine for parent process here (just after 'jc')
  1091                              <1> 	;		mov	word ptr [pid_of_child], ax
  1092                              <1> 	;		jmp	next_routine_for_parent	
  1093                              <1> 	;
  1094                              <1> 	;	@@: ; routine for child process here				
  1095                              <1> 	;		....	
  1096                              <1> 	;	NOTE: 'sysfork' returns to specified offset
  1097                              <1> 	;	       for child process by using BX input.
  1098                              <1> 	;	      (at first, parent process will return then 
  1099                              <1> 	;	      child process will return -after swapped in-
  1100                              <1> 	;	      'syswait' is needed in parent process
  1101                              <1> 	;	      if return from child process will be waited for.)
  1102                              <1> 	;	  				
  1103                              <1> 	
  1104                              <1> ; / create a new process
  1105                              <1> 	; EBX = return address for child process 
  1106                              <1> 	     ; (Retro UNIX 8086 v1 modification !)
  1107 0000D2F6 31F6                <1> 	xor 	esi, esi
  1108                              <1> 		; clr r1
  1109                              <1> sysfork_1: ; 1: / search p.stat table for unused process number
  1110 0000D2F8 46                  <1> 	inc	esi
  1111                              <1> 		; inc r1
  1112 0000D2F9 80BE[AF000300]00    <1> 	cmp	byte [esi+p.stat-1], 0 ; SFREE, 05/02/2014
  1113                              <1> 		; tstb p.stat-1(r1) / is process active, unused, dead
  1114 0000D300 760B                <1> 	jna	short sysfork_2	
  1115                              <1> 		; beq 1f / it's unused so branch
  1116 0000D302 6683FE10            <1> 	cmp	si, nproc
  1117                              <1> 		; cmp r1,$nproc / all processes checked
  1118 0000D306 72F0                <1> 	jb	short sysfork_1
  1119                              <1> 		; blt 1b / no, branch back
  1120                              <1> 	;
  1121                              <1> 	; Retro UNIX 8086 v1. modification:
  1122                              <1> 	;	Parent process returns from 'sysfork' to address 
  1123                              <1> 	;	which is just after 'sysfork' system call in parent
  1124                              <1> 	;	process. Child process returns to address which is put
  1125                              <1> 	;	in BX register by parent process for 'sysfork'. 
  1126                              <1> 	;
  1127                              <1> 		;add $2,18.(sp) / add 2 to pc when trap occured, points
  1128                              <1> 		             ; / to old process return
  1129                              <1> 		; br error1 / no room for a new process
  1130 0000D308 E96DFCFFFF          <1> 	jmp	error
  1131                              <1> sysfork_2: ; 1:
  1132 0000D30D E8D37FFFFF          <1> 	call	allocate_page
  1133 0000D312 0F8262FCFFFF        <1> 	jc	error
  1134 0000D318 50                  <1> 	push	eax   ; UPAGE (user structure page) address
  1135                              <1> 	; Retro UNIX 386 v1 modification!
  1136 0000D319 E8D681FFFF          <1> 	call	duplicate_page_dir
  1137                              <1> 		; EAX = New page directory 
  1138 0000D31E 730B                <1> 	jnc	short sysfork_3
  1139 0000D320 58                  <1> 	pop	eax   ; UPAGE (user structure page) address
  1140 0000D321 E89D81FFFF          <1> 	call 	deallocate_page
  1141 0000D326 E94FFCFFFF          <1> 	jmp	error
  1142                              <1> sysfork_3:
  1143                              <1> 	; Retro UNIX 386 v1 modification !
  1144 0000D32B 56                  <1> 	push	esi
  1145 0000D32C E8E5180000          <1> 	call	wswap ; save current user (u) structure, user registers
  1146                              <1> 		      ; and interrupt return components (for IRET)
  1147 0000D331 8705[B8030300]      <1> 	xchg	eax, [u.pgdir] ; page directory of the child process
  1148 0000D337 A3[BC030300]        <1> 	mov	[u.ppgdir], eax ; page directory of the parent process
  1149 0000D33C 5E                  <1> 	pop	esi
  1150 0000D33D 58                  <1> 	pop	eax   ; UPAGE (user structure page) address
  1151                              <1> 		; [u.usp] = esp
  1152 0000D33E 89F7                <1> 	mov	edi, esi
  1153 0000D340 66C1E702            <1> 	shl	di, 2
  1154 0000D344 8987[BC000300]      <1> 	mov	[edi+p.upage-4], eax ; memory page for 'user' struct
  1155 0000D34A A3[B4030300]        <1> 	mov	[u.upage], eax ; memory page for 'user' struct (child)
  1156                              <1> 	; 28/08/2015
  1157 0000D34F 0FB605[B3030300]    <1> 	movzx	eax, byte [u.uno] ; parent process number
  1158                              <1> 		; movb u.uno,-(sp) / save parent process number
  1159 0000D356 89C7                <1> 	mov	edi, eax
  1160 0000D358 50                  <1>         push	eax ; ** 
  1161 0000D359 8A87[7F000300]      <1> 	mov     al, [edi+p.ttyc-1] ; console tty (parent)
  1162                              <1> 	; 18/09/2015
  1163                              <1> 	;mov     [esi+p.ttyc-1], al ; set child's console tty
  1164                              <1> 	;mov     [esi+p.waitc-1], ah ; 0 ; reset child's wait channel
  1165 0000D35F 668986[7F000300]    <1> 	mov     [esi+p.ttyc-1], ax ; al - set child's console tty
  1166                              <1> 				   ; ah - reset child's wait channel	
  1167 0000D366 89F0                <1> 	mov	eax, esi
  1168 0000D368 A2[B3030300]        <1> 	mov	[u.uno], al ; child process number
  1169                              <1> 		;movb r1,u.uno / set child process number to r1
  1170 0000D36D FE86[AF000300]      <1>         inc     byte [esi+p.stat-1] ; 1, SRUN, 05/02/2014
  1171                              <1> 		; incb p.stat-1(r1) / set p.stat entry for child 
  1172                              <1> 				; / process to active status
  1173                              <1> 		; mov u.ttyp,r2 / put pointer to parent process' 
  1174                              <1> 			      ; / control tty buffer in r2
  1175                              <1>                 ; beq 2f / branch, if no such tty assigned
  1176                              <1> 		; clrb 6(r2) / clear interrupt character in tty buffer
  1177                              <1> 	; 2:
  1178 0000D373 53                  <1> 	push	ebx  ; * return address for the child process
  1179                              <1> 		     ; * Retro UNIX 8086 v1 feature only !	
  1180                              <1> 	; (Retro UNIX 8086 v1 modification!)
  1181                              <1> 		; mov $runq+4,r2
  1182 0000D374 BB[54030300]        <1> 	mov	ebx, runq+2 ; normal run queue ; 02/01/2017  
  1183 0000D379 E808190000          <1> 	call	putlu
  1184                              <1>  		; jsr r0,putlu / put child process on lowest priority 
  1185                              <1> 			   ; / run queue
  1186 0000D37E 66D1E6              <1> 	shl	si, 1
  1187                              <1> 		; asl r1 / multiply r1 by 2 to get index 
  1188                              <1> 		       ; / into p.pid table
  1189 0000D381 66FF05[4E030300]    <1> 	inc	word [mpid]
  1190                              <1> 		; inc mpid / increment m.pid; get a new process name
  1191 0000D388 66A1[4E030300]      <1> 	mov	ax, [mpid]
  1192 0000D38E 668986[1E000300]    <1> 	mov	[esi+p.pid-2], ax
  1193                              <1> 		;mov mpid,p.pid-2(r1) / put new process name 
  1194                              <1> 				    ; / in child process' name slot
  1195 0000D395 5A                  <1> 	pop	edx  ; * return address for the child process
  1196                              <1> 		     ; * Retro UNIX 8086 v1 feature only !	
  1197 0000D396 5B                  <1>   	pop	ebx  ; **
  1198                              <1> 	;mov	ebx, [esp] ; ** parent process number
  1199                              <1> 		; movb (sp),r2 / put parent process number in r2
  1200 0000D397 66D1E3              <1> 	shl 	bx, 1
  1201                              <1> 		;asl r2 / multiply by 2 to get index into below tables
  1202                              <1> 	;movzx eax, word [ebx+p.pid-2]
  1203 0000D39A 668B83[1E000300]    <1> 	mov	ax, [ebx+p.pid-2]
  1204                              <1> 		; mov p.pid-2(r2),r2 / get process name of parent
  1205                              <1> 				   ; / process
  1206 0000D3A1 668986[3E000300]    <1> 	mov	[esi+p.ppid-2], ax
  1207                              <1> 		; mov r2,p.ppid-2(r1) / put parent process name 
  1208                              <1> 			  ; / in parent process slot for child
  1209 0000D3A8 A3[64030300]        <1> 	mov	[u.r0], eax	
  1210                              <1> 		; mov r2,*u.r0 / put parent process name on stack 
  1211                              <1> 			     ; / at location where r0 was saved
  1212 0000D3AD 8B2D[5C030300]      <1> 	mov 	ebp, [u.sp] ; points to return address (EIP for IRET)
  1213 0000D3B3 895500              <1> 	mov	[ebp], edx ; *, CS:EIP -> EIP
  1214                              <1> 			   ; * return address for the child process
  1215                              <1> 		; mov $sysret1,-(sp) /
  1216                              <1> 		; mov sp,u.usp / contents of sp at the time when 
  1217                              <1> 			      ; / user is swapped out
  1218                              <1> 		; mov $sstack,sp / point sp to swapping stack space
  1219                              <1> 	; 04/09/2015 - 01/09/2015
  1220                              <1> 	; [u.usp] = esp
  1221 0000D3B6 68[9ACF0000]        <1> 	push	sysret ; ***
  1222 0000D3BB 8925[60030300]      <1> 	mov	[u.usp], esp ; points to 'sysret' address (***)
  1223                              <1> 			     ; (for child process)	
  1224 0000D3C1 31C0                <1> 	xor 	eax, eax
  1225 0000D3C3 66A3[94030300]      <1> 	mov 	[u.ttyp], ax ; 0
  1226                              <1> 	;
  1227 0000D3C9 E848180000          <1> 	call	wswap ; Retro UNIX 8086 v1 modification !
  1228                              <1> 		;jsr r0,wswap / put child process out on drum
  1229                              <1> 		;jsr r0,unpack / unpack user stack
  1230                              <1> 		;mov u.usp,sp / restore user stack pointer
  1231                              <1> 		; tst (sp)+ / bump stack pointer
  1232                              <1> 	; Retro UNIX 386 v1 modification !
  1233 0000D3CE 58                  <1> 	pop	eax ; ***
  1234 0000D3CF 66D1E3              <1> 	shl	bx, 1
  1235 0000D3D2 8B83[BC000300]      <1> 	mov     eax, [ebx+p.upage-4] ; UPAGE address ; 14/05/2015
  1236 0000D3D8 E871180000          <1> 	call	rswap ; restore parent process 'u' structure, 
  1237                              <1> 		      ; registers and return address (for IRET)
  1238                              <1> 		;movb (sp)+,u.uno / put parent process number in u.uno
  1239 0000D3DD 0FB705[4E030300]    <1>         movzx   eax, word [mpid]
  1240 0000D3E4 A3[64030300]        <1> 	mov	[u.r0], eax
  1241                              <1> 		; mov mpid,*u.r0 / put child process name on stack 
  1242                              <1> 			       ; / where r0 was saved
  1243                              <1> 		; add $2,18.(sp) / add 2 to pc on stack; gives parent
  1244                              <1> 			          ; / process return
  1245                              <1> 	;xor	ebx, ebx
  1246 0000D3E9 31F6                <1> 	xor     esi, esi
  1247                              <1> 		;clr r1
  1248                              <1> sysfork_4: ; 1: / search u.fp list to find the files 
  1249                              <1> 	      ; / opened by the parent process
  1250                              <1> 	; 01/09/2015
  1251                              <1> 	;xor	bh, bh
  1252                              <1> 	;mov 	bl, [esi+u.fp]
  1253 0000D3EB 8A86[6A030300]      <1> 	mov 	al, [esi+u.fp]
  1254                              <1> 		; movb u.fp(r1),r2 / get an open file for this process
  1255                              <1>         ;or      bl, bl
  1256 0000D3F1 08C0                <1> 	or	al, al
  1257 0000D3F3 740D                <1> 	jz	short sysfork_5	
  1258                              <1> 		; beq 2f / file has not been opened by parent, 
  1259                              <1> 		       ; / so branch
  1260 0000D3F5 B40A                <1> 	mov	ah, 10 ; Retro UNIX 386 v1 fsp structure size = 10 bytes
  1261 0000D3F7 F6E4                <1> 	mul	ah
  1262                              <1> 	;movzx	ebx, ax
  1263 0000D3F9 6689C3              <1> 	mov	bx, ax
  1264                              <1> 	;shl     bx, 3
  1265                              <1> 		; asl r2 / multiply by 8
  1266                              <1>        		; asl r2 / to get index into fsp table
  1267                              <1>        		; asl r2
  1268 0000D3FC FE83[4E010300]      <1>   	inc     byte [ebx+fsp-2]
  1269                              <1> 		; incb fsp-2(r2) / increment number of processes
  1270                              <1> 			     ; / using file, because child will now be
  1271                              <1> 			     ; / using this file
  1272                              <1> sysfork_5: ; 2:
  1273 0000D402 46                  <1>         inc     esi
  1274                              <1> 		; inc r1 / get next open file
  1275 0000D403 6683FE0A            <1>         cmp     si, 10
  1276                              <1> 		; cmp r1,$10. / 10. files is the maximum number which
  1277                              <1> 			  ; / can be opened
  1278 0000D407 72E2                <1> 	jb	short sysfork_4	
  1279                              <1> 		; blt 1b / check next entry
  1280 0000D409 E98CFBFFFF          <1> 	jmp	sysret
  1281                              <1> 		; br sysret1
  1282                              <1> 
  1283                              <1> syscreat: ; < create file >
  1284                              <1> 	; 13/11/2017
  1285                              <1> 	; 27/10/2016
  1286                              <1> 	; 25/10/2016, 26/10/2016
  1287                              <1> 	; 15/10/2016, 16/10/2016, 17/10/2016
  1288                              <1> 	; 10/10/2016 (TRDOS 386 = TRDOS v2.0) 
  1289                              <1> 	;	     -derived from INT_21H.ASM-
  1290                              <1> 	;            ("loc_INT21h_create_file")
  1291                              <1>         ; 	10/07/2011 (12/03/2011)
  1292                              <1>         ;	INT 21h Function AH = 3Ch
  1293                              <1>         ;	Create File
  1294                              <1>         ;	INPUT
  1295                              <1>         ;	   CX = Attributes
  1296                              <1>         ;          DS:DX= Address of zero terminaned path name
  1297                              <1>         ;
  1298                              <1> 	; 27/12/2015 (Retro UNIX 386 v1.1)
  1299                              <1> 	; 14/05/2015 (Retro UNIX 386 v1 - Beginning)
  1300                              <1> 	; 27/05/2013 (Retro UNIX 8086 v1)
  1301                              <1> 	;
  1302                              <1> 	; 'syscreat' called with two arguments; name and mode.
  1303                              <1> 	; u.namep points to name of the file and mode is put
  1304                              <1> 	; on the stack. 'namei' is called to get i-number of the file.		
  1305                              <1> 	; If the file aready exists, it's mode and owner remain 
  1306                              <1> 	; unchanged, but it is truncated to zero length. If the file
  1307                              <1> 	; did not exist, an i-node is created with the new mode via
  1308                              <1> 	; 'maknod' whether or not the file already existed, it is
  1309                              <1> 	; open for writing. The fsp table is then searched for a free
  1310                              <1> 	; entry. When a free entry is found, proper data is placed
  1311                              <1> 	; in it and the number of this entry is put in the u.fp list.
  1312                              <1> 	; The index to the u.fp (also know as the file descriptor)
  1313                              <1> 	; is put in the user's r0. 			
  1314                              <1> 	;
  1315                              <1> 	; Calling sequence:
  1316                              <1> 	;	syscreate; name; mode
  1317                              <1> 	; Arguments:
  1318                              <1> 	;	name - name of the file to be created
  1319                              <1> 	;	mode - mode of the file to be created
  1320                              <1> 	; Inputs: (arguments)
  1321                              <1> 	; Outputs: *u.r0 - index to u.fp list 
  1322                              <1> 	;		   (the file descriptor of new file)
  1323                              <1> 	; ...............................................................
  1324                              <1> 	;				
  1325                              <1> 	; Retro UNIX 8086 v1 modification: 
  1326                              <1> 	;       'syscreate' system call has two arguments; so,
  1327                              <1> 	;	* 1st argument, name is pointed to by BX register
  1328                              <1> 	;	* 2nd argument, mode is in CX register
  1329                              <1> 	;
  1330                              <1> 	;	AX register (will be restored via 'u.r0') will return
  1331                              <1> 	;	to the user with the file descriptor/number 
  1332                              <1> 	;	(index to u.fp list).
  1333                              <1> 	;
  1334                              <1> 	;call	arg2
  1335                              <1> 	; * name - 'u.namep' points to address of file/path name
  1336                              <1> 	;          in the user's program segment ('u.segmnt')
  1337                              <1> 	;          with offset in BX register (as sysopen argument 1).
  1338                              <1> 	; * mode - sysopen argument 2 is in CX register 
  1339                              <1> 	;          which is on top of stack.
  1340                              <1> 	;
  1341                              <1> 	; TRDOS 386 (10/10/2016)
  1342                              <1> 	;	
  1343                              <1>         ; INPUT ->
  1344                              <1>         ;	   CL = File Attributes
  1345                              <1> 	;     	      bit 0 (1) - Read only file (R)
  1346                              <1> 	;             bit 1 (1) - Hidden file (H)
  1347                              <1>         ;             bit 2 (1) - System file (R)
  1348                              <1> 	;             bit 3 (1) - Volume label/name (V)
  1349                              <1>         ;             bit 4 (1) - Subdirectory (D)
  1350                              <1> 	;	      bit 5 (1) - File has been archived (A)	 	
  1351                              <1>         ;          EBX = Pointer to filename (ASCIIZ) -path-
  1352                              <1> 	;	
  1353                              <1> 	; OUTPUT ->
  1354                              <1> 	;          eax = File/Device Handle/Number (index) (AL)
  1355                              <1> 	;          cf = 1 -> Error code in AL
  1356                              <1> 	;
  1357                              <1> 	; Modified Registers: EAX (at the return of system call)
  1358                              <1> 	;  
  1359                              <1> 	; Note: If the file is existing and it has not any one
  1360                              <1> 	;	of S,H,R,V,D attributes, it will be truncated 
  1361                              <1> 	;	to zero length; otherwise, access error will be 
  1362                              <1> 	;	returned. 
  1363                              <1> 
  1364                              <1> sysmkdir_0:
  1365 0000D40E F6C108              <1> 	test	cl, 08h ; Volume name 
  1366 0000D411 740A                <1> 	jz	short syscreat_0
  1367                              <1> 
  1368                              <1> 	; Volume name or long name creation
  1369                              <1> 	; is not permitted (in TRDOS 386)!
  1370 0000D413 B80B000000          <1> 	mov	eax, ERR_FILE_ACCESS  ; 11 ; 'permission denied !'
  1371 0000D418 E926020000          <1>         jmp	sysopen_dev_err
  1372                              <1> 
  1373                              <1> syscreat_0:
  1374                              <1>         ;mov	[u.namep], ebx
  1375 0000D41D 51                  <1> 	push	ecx
  1376 0000D41E 89DE                <1> 	mov	esi, ebx
  1377                              <1> 	; file name is forced, change directory as temporary
  1378                              <1> 	;mov	ax, 1
  1379                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset ; 17/10/2016
  1380                              <1> 	;call	set_working_path 
  1381 0000D420 E8BF2D0000          <1> 	call	set_working_path_x ; 17/10/2016	
  1382 0000D425 0F82D7000000        <1> 	jc	syscreat_err
  1383                              <1> 
  1384                              <1> 	; 16/10/2016
  1385 0000D42B 803D[376B0100]00    <1> 	cmp	byte [SWP_inv_fname], 0
  1386 0000D432 776C                <1> 	ja	short  syscreat_inv_fname ; invalid file name !
  1387                              <1> 
  1388                              <1> 	; Here, we have a valid path and also a valid file name
  1389                              <1> 	; (Working dir has been changed if the path
  1390                              <1> 	;  -file name string- had contained a dir name.)
  1391                              <1> 
  1392 0000D434 6631C0              <1> 	xor	ax, ax 
  1393                              <1> 	;mov	esi, FindFile_Name
  1394 0000D437 E8E3B6FFFF          <1> 	call	find_first_file
  1395 0000D43C 59                  <1> 	pop	ecx
  1396                              <1> 		; ESI = Directory Entry (FindFile_DirEntry) Location
  1397                              <1> 		; EDI = Directory Buffer Directory Entry Location
  1398                              <1> 		; EAX = File Size
  1399                              <1> 		;  BL = Attributes of The File/Directory
  1400                              <1> 		;  BH = Long Name Yes/No Status (>0 is YES)
  1401                              <1> 		;  DX > 0 : Ambiguous filename chars are used
  1402 0000D43D 7269                <1> 	jc	short syscreat_1 ; file not found (the good!) 
  1403                              <1> 				 ; or another error (the bad') 
  1404                              <1> 
  1405                              <1> 	; (& the uggly!) truncate file to zero length before open
  1406                              <1> 
  1407                              <1> 	;'*' and '?' already checked at 'set_working_path' stage
  1408                              <1> 	;and	dx, dx
  1409                              <1> 	;jnz	short sysmkdir_err ; permission denied 
  1410                              <1> 				   ; invalid filename chars
  1411                              <1> 
  1412                              <1> 	;test	cl, 10h ; subdirectory ?
  1413                              <1> 	;jnz	short sysmkdir_err	
  1414                              <1> 
  1415                              <1> 	; BL = File Attributes:	
  1416                              <1> 	;     	      bit 0 (1) - Read only file (R)
  1417                              <1> 	;             bit 1 (1) - Hidden file (H)
  1418                              <1>         ;             bit 2 (1) - System file (R)
  1419                              <1> 	;             bit 3 (1) - Volume label/name (V)
  1420                              <1>         ;             bit 4 (1) - Subdirectory (D)
  1421                              <1> 	;	      bit 5 (1) - File has been archived	 	
  1422                              <1> 
  1423                              <1> 	; * existing directory must not be truncated
  1424                              <1> 	;   (we don't know it is empty or not, at this stage) 
  1425                              <1> 	; * existing volume name (or a long name) can not be
  1426                              <1> 	;   re-created or truncated by 'syscreat' 	
  1427                              <1> 	; * A file with S, H, R attributes must not be truncated
  1428                              <1> 	;   (change attributes to normal, if you need truncate it)
  1429                              <1> 
  1430 0000D43F F6C31F              <1> 	test	bl, 00011111b  ; check attributes of existing file
  1431 0000D442 754E                <1> 	jnz	short sysmkdir_err
  1432                              <1> 
  1433                              <1> 	;; normal file, OK to continue...
  1434                              <1> 
  1435                              <1> 	; ESI = FindFile_DirEntry
  1436 0000D444 668B4614            <1> 	mov	ax, [esi+DirEntry_FstClusHI] ; 20
  1437 0000D448 C1E010              <1> 	shl	eax, 16 ; 13/11/2017
  1438 0000D44B 668B461A            <1> 	mov	ax, [esi+DirEntry_FstClusLO] ; 26 
  1439                              <1> 	; EAX = First cluster to be truncated/unlinked
  1440 0000D44F 57                  <1> 	push	edi
  1441 0000D450 51                  <1> 	push	ecx
  1442 0000D451 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  1443 0000D456 29C9                <1> 	sub	ecx, ecx
  1444 0000D458 8A2D[465F0100]      <1> 	mov	ch, [Current_Drv]
  1445 0000D45E 01CE                <1> 	add	esi, ecx
  1446                              <1> 	; ESI = Logical dos drive description table address
  1447 0000D460 E8C9F7FFFF          <1> 	call	truncate_cluster_chain
  1448 0000D465 59                  <1> 	pop	ecx
  1449 0000D466 5F                  <1> 	pop	edi
  1450 0000D467 7230                <1> 	jc	short syscreate_truncate_err
  1451                              <1> 
  1452                              <1> 	; 26/10/2016
  1453                              <1> 	; EDI = Directory entry address in directory buffer
  1454                              <1> 	; Update directory entry
  1455 0000D469 E848DCFFFF          <1> 	call	convert_current_date_time
  1456                              <1> 	; OUTPUT -> DX = Date in dos dir entry format
  1457                              <1>         ; 	    AX = Time in dos dir entry format	
  1458 0000D46E 66894716            <1> 	mov	[edi+DirEntry_WrtTime], ax
  1459 0000D472 66895718            <1> 	mov	[edi+DirEntry_WrtDate], dx	
  1460 0000D476 66895712            <1> 	mov	[edi+DirEntry_LastAccDate], dx
  1461 0000D47A 31C0                <1> 	xor	eax, eax ; file size = 0 
  1462 0000D47C 89471C              <1> 	mov	[edi+DirEntry_FileSize], eax ; 0
  1463 0000D47F C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 ; data changed sign	
  1464 0000D486 BE[38680100]        <1> 	mov	esi, FindFile_DirEntry
  1465 0000D48B B201                <1> 	mov	dl, 1 ; open file for writing
  1466 0000D48D E9AA000000          <1> 	jmp	sysopen_2
  1467                              <1> 
  1468                              <1> sysmkdir_err:
  1469                              <1> 	; 1 = write, 2 = read & write, >2 = invalid
  1470 0000D492 B80B000000          <1>         mov	eax, ERR_FILE_ACCESS  ; 11 ; 'permission denied !'
  1471 0000D497 EB73                <1>         jmp	short sysopen_err
  1472                              <1> 
  1473                              <1> syscreate_truncate_err:
  1474 0000D499 B812000000          <1> 	mov	eax, ERR_DRV_WRITE ; 18 ; 'disk write error !'
  1475 0000D49E EB6C                <1>         jmp	short sysopen_err
  1476                              <1> 
  1477                              <1> syscreat_inv_fname:  ; invalid file name chars 
  1478                              <1> 	; 16/10/2016
  1479 0000D4A0 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME  ; 26 ; invalid file name chars 
  1480 0000D4A5 59                  <1> 	pop	ecx
  1481 0000D4A6 EB64                <1> 	jmp	sysopen_err
  1482                              <1> 
  1483                              <1> syscreat_1:
  1484                              <1> 	; Error code in EAX
  1485 0000D4A8 3C02                <1>         cmp	al, 02h ; 'File not found' error
  1486 0000D4AA 7560                <1>         jne	sysopen_err
  1487                              <1> 
  1488 0000D4AC F6C110              <1> 	test	cl, 10h ; Directory
  1489 0000D4AF 0F852C020000        <1> 	jnz	sysmkdir_2
  1490                              <1> 
  1491                              <1> syscreat_2:
  1492 0000D4B5 BE[28680100]        <1> 	mov	esi, FindFile_Name 
  1493                              <1>         ;xor	edx, edx
  1494 0000D4BA 31C0                <1>         xor	eax, eax ; File Size  = 0
  1495 0000D4BC 31DB                <1> 	xor	ebx, ebx
  1496 0000D4BE 4B                  <1> 	dec 	ebx ; FFFFFFFFh -> create empty file 
  1497                              <1> 	            ;              (only for FAT fs) 
  1498                              <1> 	; CL = File Attributes
  1499 0000D4BF E8F8EBFFFF          <1> 	call	create_file
  1500 0000D4C4 7246                <1> 	jc	sysopen_err
  1501                              <1> 		; EAX = New file's first cluster
  1502                              <1> 		; ESI = Logical Dos Drv Descr. Table Addr.
  1503                              <1> 		; EBX = offset CreateFile_Size
  1504                              <1> 		; ECX = Sectors per cluster (<256) 
  1505                              <1> 		; EDX = Directory entry index/number (<65536)
  1506                              <1> 	; 26/10/2016
  1507                              <1> 	;mov	esi, Directory_Buffer
  1508                              <1> 	;shl	dx, 5 ; *32
  1509                              <1> 	;add	esi, edx
  1510                              <1> 	;; esi = directory entry address in directory buffer
  1511                              <1> 
  1512                              <1> 	; Here, directory entry has been created but last
  1513                              <1> 	; modification date & time of the parent dir has not
  1514                              <1> 	; been updated, yet! 
  1515                              <1> 	; (Note: Directory and FAT buffers have been updated...)
  1516                              <1>  	
  1517 0000D4C6 E824DDFFFF          <1> 	call	update_parent_dir_lmdt ; now, it is OK too!
  1518                              <1> 
  1519                              <1> 	; 25/10/2016
  1520 0000D4CB 66B80018            <1> 	mov	ax, 1800h
  1521 0000D4CF BE[28680100]        <1> 	mov	esi, FindFile_Name
  1522 0000D4D4 E846B6FFFF          <1> 	call	find_first_file
  1523 0000D4D9 7231                <1> 	jc	short sysopen_err
  1524                              <1> 
  1525                              <1> 	; Only possible error after here is 
  1526                              <1> 	; "too many open files !" error.
  1527                              <1> 	;
  1528                              <1> 	; If "syscreat" will return with that error,
  1529                              <1> 	; (the file has been created but it could not be opened)
  1530                              <1> 	; the user must retry to open this file again
  1531                              <1> 	; or must close another file before using 
  1532                              <1> 	; "sysopen" system call.
  1533                              <1> 
  1534 0000D4DB B201                <1> 	mov	dl, 1 ; open file for writing
  1535                              <1> 	; ESI = Directory Entry (FindFile_DirEntry) Location
  1536                              <1> 	; EAX = File Size (= 0)
  1537 0000D4DD EB5D                <1> 	jmp	short sysopen_2
  1538                              <1> 
  1539                              <1> sysopen: ;<open file>
  1540                              <1> 	; 26/10/2016
  1541                              <1> 	; 24/10/2016
  1542                              <1> 	; 17/10/2016
  1543                              <1> 	; 15/10/2016
  1544                              <1> 	; 06/10/2016, 07/10/2016, 08/10/2016
  1545                              <1> 	; 05/10/2016 (TRDOS 386 = TRDOS v2.0) 
  1546                              <1> 	;	     -derived from INT_21H.ASM-
  1547                              <1> 	;            ("loc_INT21h_open_file")
  1548                              <1>         ; 	26/02/2011 
  1549                              <1>         ;	INT 21h Function AH = 3Dh
  1550                              <1>         ;	Open File
  1551                              <1>         ;	INPUT
  1552                              <1>         ;	   AL= File Access Value
  1553                              <1> 	;     	     0- Open for reading
  1554                              <1> 	;            1- Open for writing
  1555                              <1>         ;            2- Open for reading and writing
  1556                              <1>         ;          DS:DX= Pointer to filename (ASCIIZ)
  1557                              <1>         ;
  1558                              <1> 	; 14/05/2015 (Retro UNIX 386 v1 - Beginning)
  1559                              <1> 	; 22/05/2013 - 27/05/2013 (Retro UNIX 8086 v1)
  1560                              <1> 	;
  1561                              <1> 	; 'sysopen' opens a file in following manner:
  1562                              <1> 	;    1) The second argument in a sysopen says whether to
  1563                              <1> 	;	open the file ro read (0) or write (>0).
  1564                              <1> 	;    2) I-node of the particular file is obtained via 'namei'.
  1565                              <1> 	;    3) The file is opened by 'iopen'.
  1566                              <1> 	;    4) Next housekeeping is performed on the fsp table
  1567                              <1> 	;	and the user's open file list - u.fp.
  1568                              <1> 	;	a) u.fp and fsp are scanned for the next available slot.
  1569                              <1> 	;	b) An entry for the file is created in the fsp table.
  1570                              <1> 	;	c) The number of this entry is put on u.fp list.
  1571                              <1> 	;	d) The file descriptor index to u.fp list is pointed
  1572                              <1> 	;	   to by u.r0.
  1573                              <1> 	;
  1574                              <1> 	; Calling sequence:
  1575                              <1> 	;	sysopen; name; mode
  1576                              <1> 	; Arguments:
  1577                              <1> 	;	name - file name or path name
  1578                              <1> 	;	mode - 0 to open for reading
  1579                              <1> 	;	       1 to open for writing
  1580                              <1> 	; Inputs: (arguments)
  1581                              <1> 	; Outputs: *u.r0 - index to u.fp list (the file descriptor)
  1582                              <1> 	;		  is put into r0's location on the stack.	
  1583                              <1> 	; ...............................................................
  1584                              <1> 	;				
  1585                              <1> 	; Retro UNIX 8086 v1 modification: 
  1586                              <1> 	;       'sysopen' system call has two arguments; so,
  1587                              <1> 	;	* 1st argument, name is pointed to by BX register
  1588                              <1> 	;	* 2nd argument, mode is in CX register
  1589                              <1> 	;
  1590                              <1> 	;	AX register (will be restored via 'u.r0') will return
  1591                              <1> 	;	to the user with the file descriptor/number 
  1592                              <1> 	;	(index to u.fp list).
  1593                              <1> 	;
  1594                              <1> 	;call	arg2
  1595                              <1> 	; * name - 'u.namep' points to address of file/path name
  1596                              <1> 	;          in the user's program segment ('u.segmnt')
  1597                              <1> 	;          with offset in BX register (as sysopen argument 1).
  1598                              <1> 	; * mode - sysopen argument 2 is in CX register 
  1599                              <1> 	;          which is on top of stack.
  1600                              <1> 	;
  1601                              <1> 	; jsr r0,arg2 / get sys args into u.namep and on stack
  1602                              <1> 	;
  1603                              <1>        	; system call registers: ebx, ecx (through 'sysenter')
  1604                              <1> 	;
  1605                              <1> 	; TRDOS 386 (05/10/2016)
  1606                              <1> 	;	
  1607                              <1>         ; INPUT ->
  1608                              <1>         ;	   CL = File Access Value (Open Mode)
  1609                              <1> 	;     	      0 - Open file for reading
  1610                              <1> 	;             1 - Open file for writing
  1611                              <1>         ;             2 - Open device for reading
  1612                              <1> 	;	      3 - Open device for writing
  1613                              <1>         ;          EBX = Pointer to filename/devicename (ASCIIZ)
  1614                              <1> 	; OUTPUT ->
  1615                              <1> 	;          eax = File/Device Handle/Number (index) (AL)
  1616                              <1> 	;          cf = 1 -> Error code in AL
  1617                              <1> 	;
  1618                              <1> 	; Modified Registers: EAX (at the return of system call)
  1619                              <1> 	;  
  1620                              <1> 
  1621 0000D4DF 80F901              <1> 	cmp	cl, 1 ; read file (0), write file (1)
  1622 0000D4E2 7614                <1> 	jna	short sysopen_0
  1623                              <1> 
  1624 0000D4E4 80F903              <1> 	cmp	cl, 3
  1625 0000D4E7 0F8640010000        <1> 	jna	sysopen_device
  1626                              <1> 
  1627                              <1> 	; Invalid access code
  1628 0000D4ED B817000000          <1> 	mov	eax, ERR_INV_PARAMETER
  1629 0000D4F2 0F874B010000        <1> 	ja	sysopen_dev_err
  1630                              <1> 
  1631                              <1> sysopen_0:
  1632                              <1> 	;mov	[u.namep], ebx
  1633 0000D4F8 51                  <1> 	push	ecx
  1634 0000D4F9 89DE                <1> 	mov	esi, ebx
  1635                              <1> 	; file name is forced, change directory as temporary
  1636                              <1> 	;mov	ax, 1
  1637                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset ; 17/10/2016
  1638                              <1> 	;call	set_working_path 
  1639 0000D4FB E8E42C0000          <1> 	call	set_working_path_x ; 17/10/2016	
  1640 0000D500 731E                <1> 	jnc	short sysopen_1
  1641                              <1> 
  1642                              <1> syscreat_err: ; ecx = file attributes (for 'syscreat')
  1643 0000D502 59                  <1> 	pop	ecx ; open mode  
  1644 0000D503 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  1645 0000D505 7505                <1> 	jnz	short sysopen_err
  1646                              <1> 	; eax = 0
  1647 0000D507 B80C000000          <1> 	mov	eax, ERR_DIR_NOT_FOUND ; Directory not found !
  1648                              <1> sysopen_err:
  1649 0000D50C A3[64030300]        <1> 	mov	[u.r0], eax
  1650 0000D511 A3[C8030300]        <1> 	mov	[u.error], eax
  1651 0000D516 E89E2D0000          <1> 	call 	reset_working_path
  1652 0000D51B E95AFAFFFF          <1> 	jmp	error
  1653                              <1> 
  1654                              <1> sysopen_1:
  1655                              <1> 	;mov	esi, FindFile_Name
  1656 0000D520 66B80018            <1>         mov	ax, 1800h ; Only files 
  1657 0000D524 E8F6B5FFFF          <1> 	call	find_first_file
  1658 0000D529 5A                  <1> 	pop	edx
  1659 0000D52A 72E0                <1> 	jc	short sysopen_err ; eax = 2 (File not found !)
  1660                              <1> 
  1661                              <1> 	; check_open_file_attr_access_code
  1662                              <1> 
  1663 0000D52C F6C307              <1>         test	bl, 7  ; system, hidden, readonly 
  1664 0000D52F 740B                <1>         jz	short sysopen_2
  1665                              <1> 
  1666 0000D531 20D2                <1> 	and	dl, dl ; 0 = read mode
  1667 0000D533 7407                <1> 	jz	short sysopen_2
  1668                              <1> 
  1669                              <1> 	; 1 = write, 2 = read & write, >2 = invalid
  1670 0000D535 B80B000000          <1>         mov	eax, ERR_FILE_ACCESS  ; 11 = 'permission denied !'
  1671 0000D53A EBD0                <1>         jmp	short sysopen_err
  1672                              <1> 
  1673                              <1> sysopen_2:
  1674                              <1> 	; esi = Directory Entry (FindFile_DirEntry) Location
  1675 0000D53C 89F3                <1> 	mov	ebx, esi
  1676 0000D53E 31F6                <1>         xor     esi, esi ; 0
  1677 0000D540 31FF                <1>         xor     edi, edi ; 0
  1678                              <1> sysopen_3: ; scan the list of entries in fsp table
  1679 0000D542 80BE[6A030300]00    <1>         cmp     byte [esi+u.fp], 0
  1680 0000D549 760F                <1>         jna     short sysopen_4 ; empty slot
  1681 0000D54B 6646                <1>         inc     si
  1682 0000D54D 6683FE0A            <1>         cmp     si, 10
  1683 0000D551 72EF                <1> 	jb	short sysopen_3
  1684                              <1> toomanyf:
  1685 0000D553 B80D000000          <1> 	mov	eax, ERR_TOO_MANY_FILES ; too many open files !
  1686 0000D558 EBB2                <1> 	jmp	short sysopen_err
  1687                              <1> 
  1688                              <1> sysopen_4: 
  1689 0000D55A 80BF[A66E0100]00    <1>         cmp     byte [edi+OF_MODE], 0 ; Scan open files table 
  1690 0000D561 760A                <1> 	jna     short sysopen_5
  1691 0000D563 6647                <1> 	inc	di
  1692 0000D565 6683FF0A            <1> 	cmp     di, OPENFILES ; max. number of open files (=10)
  1693 0000D569 72EF                <1> 	jb	short sysopen_4
  1694 0000D56B EBE6                <1> 	jmp	short toomanyf
  1695                              <1> 
  1696                              <1> sysopen_5:
  1697 0000D56D FEC2                <1> 	inc	dl
  1698 0000D56F 8897[A66E0100]      <1>         mov     [edi+OF_MODE], dl
  1699 0000D575 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  1700 0000D57B 8897[9C6E0100]      <1>         mov     [edi+OF_DRIVE], dl ; Logical DOS drive number
  1701 0000D581 66C1E702            <1> 	shl	di, 2 ; *4 (dword offset)
  1702                              <1> 
  1703 0000D585 8987[EC6E0100]      <1> 	mov	[edi+OF_SIZE], eax ; File size in bytes
  1704                              <1> 
  1705 0000D58B 668B4314            <1>         mov 	ax, [ebx+DirEntry_FstClusHI]
  1706 0000D58F C1E010              <1> 	shl	eax, 16
  1707 0000D592 668B431A            <1> 	mov 	ax, [ebx+DirEntry_FstClusLO]
  1708 0000D596 8987[746E0100]      <1> 	mov     [edi+OF_FCLUSTER], eax ; First cluster
  1709 0000D59C 8987[8C6F0100]      <1> 	mov     [edi+OF_CCLUSTER], eax ; Current cluster
  1710                              <1> 
  1711 0000D5A2 31DB                <1>         xor	ebx, ebx
  1712 0000D5A4 899F[C46E0100]      <1>         mov     [edi+OF_POINTER], ebx ; offset pointer (0)
  1713 0000D5AA 899F[B46F0100]      <1>         mov     [edi+OF_CCINDEX], ebx ; cluster index (0)
  1714                              <1> 
  1715 0000D5B0 A1[58680100]        <1> 	mov	eax, [FindFile_DirFirstCluster]
  1716 0000D5B5 8987[146F0100]      <1> 	mov	[edi+OF_DIRFCLUSTER], eax
  1717                              <1> 
  1718 0000D5BB A1[5C680100]        <1> 	mov	eax, [FindFile_DirCluster]
  1719 0000D5C0 8987[3C6F0100]      <1> 	mov	[edi+OF_DIRCLUSTER], eax
  1720                              <1> 
  1721                              <1> 	; Get (& Save) Volume ID 
  1722                              <1> 	; Important for files of removable drives
  1723                              <1> 	; (In order to check the drive has same volume/disk)
  1724 0000D5C6 88D7                <1> 	mov	bh, dl
  1725 0000D5C8 81C300010900        <1>         add	ebx, Logical_DOSDisks
  1726 0000D5CE 8A4303              <1>         mov	al, [ebx+LD_FATType]
  1727 0000D5D1 3C01                <1>         cmp	al, 1
  1728 0000D5D3 7209                <1>         jb	short sysopen_6_fs
  1729 0000D5D5 3C02                <1>         cmp	al, 2
  1730 0000D5D7 770A                <1>         ja	short sysopen_6_fat32
  1731                              <1> sysopen_6_fat:
  1732 0000D5D9 8B432D              <1>         mov	eax, [ebx+LD_BPB+VolumeID]
  1733 0000D5DC EB08                <1>         jmp	short sysopen_7
  1734                              <1> sysopen_6_fs:
  1735 0000D5DE 8B4328              <1>         mov	eax, [ebx+LD_FS_VolumeSerial]
  1736 0000D5E1 EB03                <1>         jmp	short sysopen_7
  1737                              <1> sysopen_6_fat32:
  1738 0000D5E3 8B4349              <1>         mov	eax, [ebx+LD_BPB+FAT32_VolID]
  1739                              <1> sysopen_7:
  1740 0000D5E6 A3[3C5F0100]        <1>         mov	[Current_VolSerial], eax
  1741                              <1> 
  1742 0000D5EB 8987[646F0100]      <1> 	mov	[edi+OF_VOLUMEID], eax
  1743                              <1> 
  1744                              <1> 	; 24/10/2016
  1745 0000D5F1 66D1EF              <1> 	shr	di, 1 ; 4/2, word offset
  1746 0000D5F4 668B1D[60680100]    <1> 	mov	bx, [FindFile_DirEntryNumber]
  1747 0000D5FB 66899F[DC6F0100]    <1> 	mov	[edi+OF_DIRENTRY], bx
  1748                              <1> 
  1749 0000D602 31D2                <1> 	xor	edx, edx
  1750                              <1> 	;shr	di, 2 ; /4 (byte offset)
  1751 0000D604 66D1EF              <1> 	shr	di, 1 ; 2/2, byte offset
  1752 0000D607 8897[BA6E0100]      <1> 	mov	byte [edi+OF_OPENCOUNT], dl ; 0
  1753 0000D60D 8897[B06E0100]      <1> 	mov	byte [edi+OF_STATUS], dl ; 0
  1754                              <1> 
  1755 0000D613 89FB                <1> 	mov	ebx, edi
  1756 0000D615 FEC3                <1> 	inc	bl
  1757                              <1> 
  1758 0000D617 889E[6A030300]      <1>         mov     [esi+u.fp], bl ; Open File Entry Number
  1759 0000D61D 8935[64030300]      <1> 	mov     [u.r0], esi ; move index to u.fp list 
  1760                              <1> 			    ; into eax on stack
  1761                              <1> 
  1762 0000D623 E8912C0000          <1>         call 	reset_working_path
  1763                              <1>         
  1764 0000D628 E96DF9FFFF          <1> 	jmp	sysret
  1765                              <1> 
  1766                              <1> 	; (Retro UNIX 386 v1.0)
  1767                              <1> 	; 'fsp' table (10 bytes/entry)
  1768                              <1> 	; bit 15				   bit 0
  1769                              <1> 	; ---|-------------------------------------------
  1770                              <1> 	; r/w|		i-number of open file
  1771                              <1> 	; ---|-------------------------------------------
  1772                              <1> 	;		   device number
  1773                              <1> 	; -----------------------------------------------
  1774                              <1> 	; offset pointer, r/w pointer to file (bit 0-15)
  1775                              <1> 	; -----------------------------------------------
  1776                              <1> 	; offset pointer, r/w pointer to file (bit 16-31)
  1777                              <1> 	; ----------------------|------------------------
  1778                              <1> 	;  flag that says file 	| number of processes
  1779                              <1> 	;   has been deleted	| that have file open 
  1780                              <1> 	; ----------------------|------------------------
  1781                              <1> 
  1782                              <1> sysopen_device:
  1783                              <1> 	; 15/10/2016
  1784                              <1> 	; 08/10/2016
  1785                              <1> 	; 07/10/2016 (TRDOS 386 = TRDOS v2.0)
  1786 0000D62D 51                  <1> 	push	ecx ; open mode
  1787 0000D62E 89E5                <1> 	mov	ebp, esp
  1788 0000D630 B910000000          <1> 	mov	ecx, 16 ; transfer length = 16 bytes 
  1789 0000D635 29CC                <1> 	sub	esp, ecx
  1790 0000D637 89E7                <1> 	mov	edi, esp ; destination address 
  1791 0000D639 89DE                <1> 	mov 	esi, ebx ; dev name in user's memory space
  1792 0000D63B E86C170000          <1> 	call	transfer_from_user_buffer
  1793 0000D640 7310                <1> 	jnc	short sysopen_dev_0
  1794                              <1> 	; eax = ERR_OUT_OF_MEMORY = 4 = ERR_MINOR_IM
  1795 0000D642 59                  <1> 	pop	ecx
  1796                              <1> sysopen_dev_err:
  1797 0000D643 A3[64030300]        <1> 	mov	[u.r0], eax
  1798 0000D648 A3[C8030300]        <1> 	mov	[u.error], eax
  1799 0000D64D E928F9FFFF          <1> 	jmp	error
  1800                              <1> sysopen_dev_0:
  1801 0000D652 89FE                <1> 	mov	esi, edi ; Device name addr (max. 16 bytes, ASCIIZ) 
  1802                              <1> 			 ; for example: "tty, TTY, /dev/tty"
  1803 0000D654 E8062F0000          <1> 	call	get_device_number
  1804 0000D659 89EC                <1> 	mov	esp, ebp
  1805 0000D65B 59                  <1> 	pop	ecx
  1806 0000D65C 7307                <1> 	jnc	short sysopen_dev_1
  1807 0000D65E B818000000          <1> 	mov	eax, ERR_INV_DEV_NAME ; 24 ; 'invalid device name !'
  1808 0000D663 EBDE                <1> 	jmp	short sysopen_dev_err
  1809                              <1> sysopen_dev_1:
  1810                              <1> 	; eax = Device Number (AL)
  1811                              <1> 	;  cl = Open mode (2 = device read, 3 = device write)
  1812 0000D665 31DB                <1>         xor     ebx, ebx ; 0
  1813                              <1> sysopen_dev_2: ; scan the list of entries
  1814 0000D667 389B[6A030300]      <1>         cmp     [ebx+u.fp], bl ; 0
  1815 0000D66D 760E                <1>         jna     short sysopen_dev_3 ; empty slot
  1816 0000D66F FEC3                <1>         inc     bl
  1817 0000D671 80FB0A              <1>         cmp     bl, 10
  1818 0000D674 72F1                <1> 	jb	short sysopen_dev_2
  1819                              <1> 	;
  1820 0000D676 B80D000000          <1> 	mov	eax, ERR_TOO_MANY_FILES ; too many open files !
  1821 0000D67B EBC6                <1> 	jmp	short sysopen_dev_err
  1822                              <1> sysopen_dev_3:
  1823 0000D67D 891D[64030300]      <1> 	mov 	[u.r0], ebx ; File/Device index/handle/descriptor
  1824                              <1> 	; eax = device number (entry offset)
  1825 0000D683 8AA8[386C0100]      <1> 	mov	ch, [eax+DEV_ACCESS] ; bit 0 = accessable by users
  1826                              <1> 				     ; bit 1 = read access perm
  1827                              <1> 				     ; bit 2 = write access perm
  1828                              <1> 				     ; bit 3 = IOCTL permit to users
  1829                              <1> 				     ; bit 4 = block device if set
  1830                              <1> 				     ; bit 5 = 16 bit or 1024 byte
  1831                              <1> 				     ; bit 6 = 32 bit or 2048 byte
  1832                              <1> 				     ; bit 7 = installable device drv
  1833 0000D689 F6C501              <1> 	test 	ch, 1 ; accessable by normal users (except root)
  1834 0000D68C 7510                <1> 	jnz	short sysopen_dev_4 ; yes, permission has been given
  1835 0000D68E 803D[B0030300]00    <1> 	cmp	byte [u.uid], 0 ; root?
  1836 0000D695 7607                <1> 	jna	short sysopen_dev_4 ; superuser can open all devices
  1837                              <1> sysopen_dev_perm_err:
  1838 0000D697 B80B000000          <1> 	mov	eax, ERR_DEV_ACCESS  ; 11 = 'permission denied !'
  1839 0000D69C EBA5                <1> 	jmp	short sysopen_dev_err
  1840                              <1> sysopen_dev_4:
  1841 0000D69E D0ED                <1> 	shr	ch, 1 ; result: 1 = read, 2 = write, 3 = r & w 
  1842 0000D6A0 FEC9                <1> 	dec	cl  ; result: 1 = read, 2 = write
  1843 0000D6A2 84E9                <1> 	test	cl, ch
  1844 0000D6A4 74F1                <1> 	jz	short sysopen_dev_perm_err 
  1845                              <1> 
  1846 0000D6A6 D0E5                <1> 	shl	ch, 1 ; bit 0 = 0
  1847                              <1> 	; eax = device number (entry offset)
  1848 0000D6A8 E8CE2F0000          <1> 	call	device_open
  1849 0000D6AD 72E8                <1> 	jc	short sysopen_dev_perm_err 
  1850                              <1> 
  1851                              <1> 	; eax = device number (entry offset)
  1852 0000D6AF 0C80                <1> 	or	al, 80h ; set device bit (set bit 7 to 1)
  1853 0000D6B1 8B1D[64030300]      <1> 	mov	ebx, [u.r0]
  1854 0000D6B7 8883[6A030300]      <1> 	mov	[ebx+u.fp], al	; bit 7 (=1) points to device	
  1855                              <1> 	
  1856 0000D6BD E9D8F8FFFF          <1> 	jmp	sysret
  1857                              <1> 
  1858                              <1> sysmkdir: ; < make directory >
  1859                              <1> 	; 15/10/2016
  1860                              <1> 	; 10/10/2016 (TRDOS 386 = TRDOS v2.0) 
  1861                              <1> 	;	     -derived from INT_21H.ASM-
  1862                              <1> 	;            ("loc_INT21h_create_file")
  1863                              <1>         ; 	10/07/2011 (12/03/2011)
  1864                              <1>         ;	INT 21h Function AH = 3Ch
  1865                              <1>         ;	Create File
  1866                              <1>         ;	INPUT
  1867                              <1>         ;	   CX = Attributes
  1868                              <1>         ;          DS:DX= Address of zero terminaned path name
  1869                              <1>         ;
  1870                              <1>         ;
  1871                              <1> 	; 14/05/2015 (Retro UNIX 386 v1 - Beginning)
  1872                              <1> 	; 27/05/2013 - 02/08/2013 (Retro UNIX 8086 v1)
  1873                              <1> 	;
  1874                              <1> 	; 'sysmkdir' creates an empty directory whose name is
  1875                              <1> 	; pointed to by arg 1. The mode of the directory is arg 2.	
  1876                              <1> 	; The special entries '.' and '..' are not present.
  1877                              <1> 	; Errors are indicated if the directory already exists or		
  1878                              <1> 	; user is not the super user. 
  1879                              <1> 	;
  1880                              <1> 	; Calling sequence:
  1881                              <1> 	;	sysmkdir; name; mode
  1882                              <1> 	; Arguments:
  1883                              <1> 	;	name - points to the name of the directory
  1884                              <1> 	;	mode - mode of the directory
  1885                              <1> 	; Inputs: (arguments)
  1886                              <1> 	; Outputs: -
  1887                              <1> 	;    (sets 'directory' flag to 1; 
  1888                              <1> 	;    'set user id on execution' and 'executable' flags to 0)
  1889                              <1> 	; ...............................................................
  1890                              <1> 	;				
  1891                              <1> 	; Retro UNIX 8086 v1 modification: 
  1892                              <1> 	;       'sysmkdir' system call has two arguments; so,
  1893                              <1> 	;	* 1st argument, name is pointed to by BX register
  1894                              <1> 	;	* 2nd argument, mode is in CX register
  1895                              <1> 	;
  1896                              <1> 	; TRDOS 386 (10/10/2016)
  1897                              <1> 	;	
  1898                              <1>         ; INPUT ->
  1899                              <1>         ;	   CL = Directory Attributes
  1900                              <1> 	;     	      bit 0 (1) - Read only file/dir (R)
  1901                              <1> 	;             bit 1 (1) - Hidden file/dir (H)
  1902                              <1>         ;             bit 2 (1) - System file/dir (R)
  1903                              <1> 	;             bit 3 (1) - Volume label/name (V)
  1904                              <1>         ;             bit 4 (1) - Subdirectory (D)
  1905                              <1> 	;	      bit 5 (1) - File/Dir has been archived (A)
  1906                              <1> 	;	   CX = 0 -> create normal directory	 	
  1907                              <1>         ;          EBX = Pointer to directory name (ASCIIZ) -path-
  1908                              <1> 	;	
  1909                              <1> 	; OUTPUT ->
  1910                              <1> 	;          eax = First cluster of the new directory
  1911                              <1> 	;          cf = 1 -> Error code in AL
  1912                              <1> 	;
  1913                              <1> 	; Modified Registers: EAX (at the return of system call)
  1914                              <1> 	;  
  1915                              <1> 	; Note: If the file or directory is existing
  1916                              <1> 	;	an access error will be returned. 
  1917                              <1> 
  1918 0000D6C2 6621C9              <1> 	and	cx, cx ; if cx = 0 -> create a normal subdir
  1919 0000D6C5 7413                <1> 	jz	short sysmkdir_1
  1920                              <1> 
  1921 0000D6C7 F6C110              <1> 	test	cl, 10h ; if dir flags set, also use other flags
  1922 0000D6CA 0F853EFDFFFF        <1> 	jnz	sysmkdir_0 ; jump to head of 'syscreat'
  1923                              <1> 
  1924                              <1> 	; CX has wrong flags
  1925 0000D6D0 B817000000          <1> 	mov 	eax, ERR_INV_FLAGS
  1926 0000D6D5 E969FFFFFF          <1> 	jmp	sysopen_dev_err
  1927                              <1> 
  1928                              <1> sysmkdir_1:
  1929 0000D6DA B110                <1> 	mov	cl, 10h ; set subdir flag and reset other flags
  1930 0000D6DC E92DFDFFFF          <1> 	jmp	sysmkdir_0 ; jump to head of 'syscreat'
  1931                              <1> sysmkdir_2: 
  1932                              <1> 	; jump from 'syscreat' ; from 'syscreat_1'
  1933                              <1> 	;  CL = Directory attributes/flags  
  1934 0000D6E1 BE[28680100]        <1> 	mov	esi, FindFile_Name 
  1935 0000D6E6 E804D7FFFF          <1> 	call	make_sub_directory
  1936 0000D6EB 0F821BFEFFFF        <1> 	jc	sysopen_err       ; NOTE: Old type (TRDOS 8086)
  1937                              <1> 				  ; error codes must be modified
  1938                              <1> 				  ; for next TRDOS 386 versions
  1939                              <1> 				  ; (10/10/2016)
  1940                              <1> 				  ; Old (MSDOS type)
  1941                              <1> 				  ; error codes (2011):
  1942                              <1> 				  ;  2 = file not found
  1943                              <1> 				  ;  3 = directory not found
  1944                              <1> 				  ;  5 = access denied
  1945                              <1> 				  ; 12 = no more files
  1946                              <1> 			          ; 19 = disk write protected   
  1947                              <1> 				  ; 39 = insufficient disk space
  1948                              <1> 				  ; 'sysdefs.s' ; 10/10/2016  	
  1949                              <1> 	
  1950 0000D6F1 A3[64030300]        <1> 	mov	[u.r0], eax ; New sub dir's first cluster
  1951                              <1> 
  1952 0000D6F6 E8BE2B0000          <1>         call 	reset_working_path
  1953                              <1> 
  1954 0000D6FB E99AF8FFFF          <1> 	jmp	sysret	
  1955                              <1> 
  1956                              <1> sysclose: ;<close file>
  1957                              <1> 	; 06/10/2016 (TRDOS 386 = TRDOS v2.0) 
  1958                              <1> 	;
  1959                              <1> 	; 14/05/2015 (Retro UNIX 386 v1 - Beginning)
  1960                              <1> 	; 22/05/2013 - 26/05/2013 (Retro UNIX 8086 v1)
  1961                              <1> 	;
  1962                              <1> 	; 'sysclose', given a file descriptor in 'u.r0', closes the
  1963                              <1> 	; associated file. The file descriptor (index to 'u.fp' list)
  1964                              <1> 	; is put in r1 and 'fclose' is called.
  1965                              <1> 	;
  1966                              <1> 	; Calling sequence:
  1967                              <1> 	;	sysclose
  1968                              <1> 	; Arguments:
  1969                              <1> 	;	-  
  1970                              <1> 	; Inputs: *u.r0 - file descriptor
  1971                              <1> 	; Outputs: -
  1972                              <1> 	; ...............................................................
  1973                              <1> 	;				
  1974                              <1> 	; Retro UNIX 8086 v1 modification:
  1975                              <1> 	;	 The user/application program puts file descriptor
  1976                              <1> 	;        in BX register as 'sysclose' system call argument.
  1977                              <1> 	; 	 (argument transfer method 1)
  1978                              <1> 
  1979                              <1> 	; TRDOS 386 (06/10/2016)
  1980                              <1> 	;	
  1981                              <1>         ; INPUT ->
  1982                              <1>         ;	   EBX = File Handle/Number (file index) (AL)
  1983                              <1> 	; OUTPUT ->
  1984                              <1> 	;          cf = 0 -> EAX = 0
  1985                              <1> 	;          cf = 1 -> Error code in EAX (ERR_FILE_NOT_OPEN)
  1986                              <1> 	;
  1987                              <1> 	; Modified Registers: EAX (at the return of system call)
  1988                              <1> 	;  
  1989                              <1> 
  1990 0000D700 89D8                <1> 	mov 	eax, ebx
  1991 0000D702 31DB                <1> 	xor	ebx, ebx	
  1992 0000D704 891D[64030300]      <1> 	mov	[u.r0], ebx ; 0  ; return value of EAX
  1993 0000D70A E8720B0000          <1> 	call 	fclose
  1994 0000D70F 0F8385F8FFFF        <1> 	jnc	sysret
  1995 0000D715 B80A000000          <1> 	mov	eax, ERR_FILE_NOT_OPEN ; file not open !
  1996 0000D71A A3[C8030300]        <1> 	mov	[u.error], eax ;
  1997 0000D71F A3[64030300]        <1> 	mov	[u.r0], eax ; ! invalid handle !
  1998 0000D724 E951F8FFFF          <1> 	jmp	error
  1999                              <1> 
  2000                              <1> sysread: ; < read from file >
  2001                              <1> 	; 11/10/2016 (TRDOS 386 = TRDOS v2.0) 
  2002                              <1> 	;	     -derived from INT_21H.ASM-
  2003                              <1> 	;            ("loc_INT21h_read_file")
  2004                              <1>         ; 	13/03/2011 (05/03/2011)
  2005                              <1>         ;	INT 21h Function AH = 3Fh
  2006                              <1>         ;	Read from a File
  2007                              <1>         ;	INPUT
  2008                              <1> 	;	   BX = File Handle
  2009                              <1>         ;	   CX = Number of bytes to read
  2010                              <1>         ;          DS:DX= Buffer address
  2011                              <1>         ;
  2012                              <1> 	; Note: TRDOS 386 'sysread' has been derived from 
  2013                              <1> 	;	Retro UNIX 386 v1 'sysread', except a few 
  2014                              <1> 	;	code modifications.
  2015                              <1> 	;
  2016                              <1> 	; 13/05/2015 (Retro UNIX 386 v1)
  2017                              <1> 	; 11/05/2015 (Retro UNIX 386 v1 - Beginning)
  2018                              <1> 	; 23/05/2013 (Retro UNIX 8086 v1)
  2019                              <1> 	;
  2020                              <1> 	; 'sysread' is given a buffer to read into and the number of
  2021                              <1> 	; characters to be read. If finds the file from the file
  2022                              <1> 	; descriptor located in *u.r0 (r0). This file descriptor
  2023                              <1> 	; is returned from a successful open call (sysopen).
  2024                              <1> 	; The i-number of file is obtained via 'rw1' and the data
  2025                              <1> 	; is read into core via 'readi'.
  2026                              <1> 	;
  2027                              <1> 	; Calling sequence:
  2028                              <1> 	;	sysread; buffer; nchars
  2029                              <1> 	; Arguments:
  2030                              <1> 	;	buffer - location of contiguous bytes where 
  2031                              <1> 	;		 input will be placed.
  2032                              <1> 	;	nchars - number of bytes or characters to be read.
  2033                              <1> 	; Inputs: *u.r0 - file descriptor (& arguments)
  2034                              <1> 	; Outputs: *u.r0 - number of bytes read.	
  2035                              <1> 	; ...............................................................
  2036                              <1> 	;				
  2037                              <1> 	; Retro UNIX 8086 v1 modification: 
  2038                              <1> 	;       'sysread' system call has three arguments; so,
  2039                              <1> 	;	* 1st argument, file descriptor is in BX register
  2040                              <1> 	;	* 2nd argument, buffer address/offset in CX register
  2041                              <1> 	;	* 3rd argument, number of bytes is in DX register
  2042                              <1> 	;
  2043                              <1> 	;	AX register (will be restored via 'u.r0') will return
  2044                              <1> 	;	to the user with number of bytes read. 
  2045                              <1> 	;
  2046                              <1> 	; TRDOS 386 (05/10/2016)
  2047                              <1> 	;	
  2048                              <1>         ; INPUT ->
  2049                              <1>         ;	   EBX = File handle (descriptor/index)
  2050                              <1> 	;	   ECX = Buffer address		
  2051                              <1>         ;          EDX = Number of bytes
  2052                              <1> 	; OUTPUT ->
  2053                              <1> 	;          EAX = Number of bytes have been read
  2054                              <1> 	;          cf = 1 -> Error code in AL
  2055                              <1> 	;
  2056                              <1> 	; Modified Registers: EAX (at the return of system call)
  2057                              <1> 	; 
  2058                              <1> 
  2059                              <1> 	; EBX = File descriptor
  2060 0000D729 E8A10B0000          <1> 	call	getf1 
  2061 0000D72E 7277                <1> 	jc	short device_read ; read data from device
  2062                              <1> 	; EAX = First cluster of the file
  2063                              <1> 
  2064 0000D730 E83F000000          <1> 	call	rw1
  2065 0000D735 730A                <1> 	jnc	short sysread_0
  2066                              <1> 
  2067 0000D737 A3[64030300]        <1> 	mov	[u.r0], eax ; error code
  2068 0000D73C E939F8FFFF          <1> 	jmp	error
  2069                              <1> 	 
  2070                              <1> sysread_0:
  2071 0000D741 E852110000          <1> 	call	readi
  2072 0000D746 EB1D                <1> 	jmp	short rw0
  2073                              <1> 
  2074                              <1> syswrite: ; < write to file >
  2075                              <1> 	; 23/10/2016
  2076                              <1> 	; 11/10/2016 (TRDOS 386 = TRDOS v2.0) 
  2077                              <1> 	;	     -derived from INT_21H.ASM-
  2078                              <1> 	;            ("loc_INT21h_write_file")
  2079                              <1>         ; 	13/03/2011 (05/03/2011)
  2080                              <1>         ;	INT 21h Function AH = 40h
  2081                              <1>         ;	Write to a File
  2082                              <1>         ;	INPUT
  2083                              <1> 	;	   BX = File Handle
  2084                              <1>         ;	   CX = Number of bytes to write
  2085                              <1>         ;          DS:DX= Buffer address
  2086                              <1>         ;
  2087                              <1> 	; Note: TRDOS 386 'sysrwrite' has been derived from 
  2088                              <1> 	;	Retro UNIX 386 v1 'syswrite', except a few 
  2089                              <1> 	;	code modifications.
  2090                              <1> 	;
  2091                              <1> 
  2092                              <1> 	; 13/05/2015 (Retro UNIX 386 v1)
  2093                              <1> 	; 11/05/2015 (Retro UNIX 386 v1 - Beginning)
  2094                              <1> 	; 23/05/2013 (Retro UNIX 8086 v1)
  2095                              <1> 	;
  2096                              <1> 	; 'syswrite' is given a buffer to write onto an output file
  2097                              <1> 	; and the number of characters to write. If finds the file
  2098                              <1> 	; from the file descriptor located in *u.r0 (r0). This file 
  2099                              <1> 	; descriptor is returned from a successful open or create call
  2100                              <1> 	; (sysopen or syscreat). The i-number of file is obtained via
  2101                              <1> 	; 'rw1' and buffer is written on the output file via 'write'.
  2102                              <1> 	;
  2103                              <1> 	; Calling sequence:
  2104                              <1> 	;	syswrite; buffer; nchars
  2105                              <1> 	; Arguments:
  2106                              <1> 	;	buffer - location of contiguous bytes to be writtten.
  2107                              <1> 	;	nchars - number of characters to be written.
  2108                              <1> 	; Inputs: *u.r0 - file descriptor (& arguments)
  2109                              <1> 	; Outputs: *u.r0 - number of bytes written.	
  2110                              <1> 	; ...............................................................
  2111                              <1> 	;				
  2112                              <1> 	; Retro UNIX 8086 v1 modification: 
  2113                              <1> 	;       'syswrite' system call has three arguments; so,
  2114                              <1> 	;	* 1st argument, file descriptor is in BX register
  2115                              <1> 	;	* 2nd argument, buffer address/offset in CX register
  2116                              <1> 	;	* 3rd argument, number of bytes is in DX register
  2117                              <1> 	;
  2118                              <1> 	;	AX register (will be restored via 'u.r0') will return
  2119                              <1> 	;	to the user with number of bytes written. 
  2120                              <1> 	;
  2121                              <1> 	; INPUT ->
  2122                              <1>         ;	   EBX = File handle (descriptor/index)
  2123                              <1> 	;	   ECX = Buffer address		
  2124                              <1>         ;          EDX = Number of bytes
  2125                              <1> 	; OUTPUT ->
  2126                              <1> 	;          EAX = Number of bytes have been written
  2127                              <1> 	;          cf = 1 -> Error code in AL
  2128                              <1> 	;
  2129                              <1> 	; Modified Registers: EAX (at the return of system call)
  2130                              <1> 	;  
  2131                              <1> 
  2132                              <1> 	; EBX = File descriptor
  2133 0000D748 E8820B0000          <1> 	call	getf1 
  2134 0000D74D 7274                <1> 	jc	short device_write ; write data to device
  2135                              <1> 	; EAX = First cluster of the file
  2136                              <1> 	; EBX = File number  (Open file number) ; 23/10/2016
  2137                              <1> 
  2138 0000D74F E820000000          <1> 	call	rw1
  2139 0000D754 730A                <1> 	jnc	short syswrite_0
  2140 0000D756 A3[64030300]        <1> 	mov	[u.r0], eax ; error code
  2141 0000D75B E91AF8FFFF          <1> 	jmp	error
  2142                              <1> 	 
  2143                              <1> syswrite_0:
  2144 0000D760 E85F180000          <1> 	call	writei
  2145                              <1> rw0: ; 1:
  2146 0000D765 A1[8C030300]        <1>         mov	eax, [u.nread]
  2147 0000D76A A3[64030300]        <1> 	mov	[u.r0], eax
  2148 0000D76F E926F8FFFF          <1> 	jmp	sysret
  2149                              <1> 
  2150                              <1> rw1:	
  2151                              <1> 	; 11/10/2016 (TRDOS 386 = TRDOS v2.0) 
  2152                              <1> 	; 14/05/2015 (Retro UNIX 386 v1)
  2153                              <1> 	; 11/05/2015 (Retro UNIX 386 v1 - Beginning)
  2154                              <1> 	; 23/05/2013 - 24/05/2013 (Retro UNIX 8086 v1)
  2155                              <1> 	; System call registers: ebx, ecx, edx (through 'sysenter')
  2156                              <1> 	;
  2157                              <1> 	; EBX = File descriptor
  2158                              <1> 	;call	getf1 ; calling point in 'getf' from 'rw1'
  2159                              <1> 	;jc	short device_rw ; read/write data from/to device
  2160                              <1> 	; EAX = First cluster of the file
  2161                              <1> 
  2162 0000D774 83F802              <1> 	cmp 	eax, 2
  2163 0000D777 7217                <1> 	jb	short rw2
  2164                              <1> 	;
  2165 0000D779 890D[84030300]      <1> 	mov	[u.base], ecx 	; buffer address/offset 
  2166                              <1> 				;(in the user's virtual memory space)
  2167 0000D77F 8915[88030300]      <1> 	mov	[u.count], edx 
  2168                              <1> 
  2169 0000D785 C705[C8030300]0000- <1>         mov     dword [u.error], 0 ; reset the last error code
  2169 0000D78D 0000                <1>
  2170 0000D78F C3                  <1> 	retn
  2171                              <1> 
  2172                              <1> rw2:
  2173 0000D790 B80A000000          <1> 	mov	eax, ERR_FILE_NOT_OPEN ; file not open !
  2174 0000D795 A3[C8030300]        <1> 	mov	dword [u.error], eax
  2175 0000D79A C3                  <1> 	retn
  2176                              <1> rw3: 
  2177 0000D79B B80B000000          <1> 	mov	eax, ERR_FILE_ACCESS ; permission denied !
  2178 0000D7A0 A3[C8030300]        <1> 	mov	dword [u.error], eax
  2179 0000D7A5 F9                  <1> 	stc
  2180 0000D7A6 C3                  <1> 	retn
  2181                              <1> 
  2182                              <1> device_read:
  2183                              <1> 	; 11/10/2016 (TRDOS 386 = TRDOS v2.0)
  2184                              <1> 	; cl = DEV_OPENMODE ; open mode
  2185                              <1> 	; ch = DEV_ACCESS   ; access flags   
  2186                              <1> 	; al = DEV_DRIVER   ; device number (eax)
  2187                              <1> 
  2188 0000D7A7 F6C101              <1> 	test	cl, 1 ; 1 = read, 2 = write, 3 = read&write
  2189 0000D7AA 74EF                <1> 	jz	short rw3
  2190                              <1> 
  2191 0000D7AC 89C3                <1> 	mov	ebx, eax
  2192 0000D7AE 66C1E302            <1> 	shl	bx, 2 ; *4
  2193                              <1> 
  2194 0000D7B2 F6C580              <1> 	test	ch, 80h ; bit 7, installable device driver flag
  2195 0000D7B5 7406                <1> 	jz	short d_read_2 ; Kernel device
  2196                              <1> 	; installable device
  2197                              <1> d_read_1:
  2198 0000D7B7 FFA3[F46B0100]      <1>         jmp	dword [ebx+IDEV_RADDR-4]
  2199                              <1> d_read_2:
  2200 0000D7BD FFA3[441B0100]      <1> 	jmp	dword [ebx+KDEV_RADDR-4]
  2201                              <1> 
  2202                              <1> device_write:
  2203                              <1> 	; 11/10/2016 (TRDOS 386 = TRDOS v2.0)
  2204                              <1> 	; cl = DEV_OPENMODE ; open mode
  2205                              <1> 	; ch = DEV_ACCESS   ; access flags   
  2206                              <1> 	; al = DEV_DRIVER   ; device number (eax)
  2207                              <1> 
  2208 0000D7C3 F6C102              <1> 	test	cl, 2 ; 1 = read, 2 = write, 3 = read&write
  2209 0000D7C6 74D3                <1> 	jz	short rw3	
  2210                              <1> 
  2211 0000D7C8 89C3                <1> 	mov	ebx, eax
  2212 0000D7CA 66C1E302            <1> 	shl	bx, 2 ; *4
  2213                              <1> 
  2214 0000D7CE F6C580              <1> 	test	ch, 80h ; bit 7, installable device driver flag
  2215 0000D7D1 7406                <1> 	jz	short d_write_2 ; Kernel device
  2216                              <1> 	; installable device
  2217                              <1> d_write_1:
  2218 0000D7D3 FFA3[146C0100]      <1>         jmp	dword [ebx+IDEV_WADDR-4]
  2219                              <1> d_write_2:
  2220 0000D7D9 FFA3[941B0100]      <1> 	jmp	dword [ebx+KDEV_WADDR-4]
  2221                              <1> 
  2222                              <1> 
  2223                              <1> sysemt: ; enable (or disable) multi tasking -time sharing-
  2224                              <1> 	;
  2225                              <1> 	; 23/05/2016 - TRDOS 386 (TRDOS v2.0)
  2226                              <1> 	; 14/05/2015 (Retro UNIX 386 v1)
  2227                              <1> 	; 10/12/2013 - 20/04/2014 (Retro UNIX 8086 v1)
  2228                              <1> 	;
  2229                              <1> 	; Retro UNIX 8086 v1 modification: 
  2230                              <1> 	;	'Enable Multi Tasking'  system call instead 
  2231                              <1> 	;	of 'Emulator Trap' in original UNIX v1 for PDP-11.
  2232                              <1> 	;
  2233                              <1> 	; Retro UNIX 8086 v1 feature only!
  2234                              <1> 	;	Using purpose: Kernel will start without time-out
  2235                              <1> 	;	(internal clock/timer) functionality.
  2236                              <1> 	;	Then etc/init will enable clock/timer for
  2237                              <1> 	;	multi tasking. 
  2238                              <1> 	;
  2239                              <1> 	; INPUT ->
  2240                              <1> 	;	BL = 0 -> disable multi tasking
  2241                              <1> 	;	BL > 1 -> enable multi tasking (time sharing) 
  2242                              <1> 	; OUTPUT ->
  2243                              <1> 	;	none	
  2244                              <1> 	;
  2245                              <1> 	;  Note: Multi tasking is disabled during system
  2246                              <1> 	;	 initialization, it must be enabled by using
  2247                              <1> 	;	 this system call. (Otherwise, running proces 
  2248                              <1> 	;	 will not be changed by another process within
  2249                              <1> 	;	 run time sequence/schedule, if running process
  2250                              <1> 	;	 will not 'release' itself. Only 'wakeup' procedure
  2251                              <1> 	;	 for waiting processes and programmed timer events
  2252                              <1> 	;	 for other processes can change running process 
  2253                              <1> 	;	 while multi tasking is disabled.) ** 23/05/2016 **
  2254                              <1> 
  2255 0000D7DF 803D[B0030300]00    <1> 	cmp	byte [u.uid], 0 ; root ?
  2256                              <1> 	;ja	error
  2257 0000D7E6 0F87D3F8FFFF        <1> 	ja	badsys ; 14/05/2015
  2258                              <1> 	;
  2259 0000D7EC FA                  <1> 	cli
  2260 0000D7ED 881D[126B0100]      <1> 	mov	[multi_tasking], bl ; 0 to disable, >0 to enable
  2261 0000D7F3 E9A2F7FFFF          <1> 	jmp	sysret
  2262                              <1> 
  2263                              <1> systimer:
  2264                              <1> 	; 02/01/2017
  2265                              <1> 	; 21/12/2016
  2266                              <1> 	; 19/12/2016
  2267                              <1> 	; 10/12/2016 (callback)
  2268                              <1> 	; 10/06/2016
  2269                              <1> 	; 07/06/2016
  2270                              <1> 	; 06/06/2016
  2271                              <1> 	; 21/05/2016
  2272                              <1> 	; 19/05/2016
  2273                              <1> 	; 18/05/2016 - TRDOS 386 (TRDOS v2.0)
  2274                              <1> 	; (TRDOS 386 feature only!)
  2275                              <1> 	;
  2276                              <1> 	; (start or stop timer event(s))	
  2277                              <1> 	;
  2278                              <1> 	; INPUT ->
  2279                              <1> 	;	BL = Signal return byte (response byte)
  2280                              <1> 	;	     (Any requested value between 0 and 255)
  2281                              <1> 	;	     (Kernel will put it at the requested address)    	
  2282                              <1> 	;	BH = Time count unit
  2283                              <1> 	;	     0 = Stop timer event
  2284                              <1> 	;	     1 = 18.2 ticks per second
  2285                              <1> 	;	     2 = 10 milliseconds  		
  2286                              <1> 	;	     3 = 1 second (for real time clock interrupt) 	 
  2287                              <1> 	;	     4 = time/tick count in current time count unit
  2288                              <1> 	;	    // 10/12/2016			
  2289                              <1> 	;	    80h = Stop timer event (callback method)
  2290                              <1> 	;	    81h = 18.2 ticks per second, callback method
  2291                              <1> 	;	    82h = 10 milliseconds, callback method 	
  2292                              <1> 	;	    83h = 1 second (for RTC int), callback method 	
  2293                              <1> 	;	    84h = current time count unit, callback method
  2294                              <1> 	;
  2295                              <1> 	;	    Note: Only 03h or 83h will set real time clock
  2296                              <1> 	;		  (RTC) events (Others are for PIT events)! 	
  2297                              <1> 	;	
  2298                              <1> 	;	NOTE: If callback (user service) method is used,
  2299                              <1> 	;	    EDX will point to the return address (of service
  2300                              <1> 	;	    procedure) in user's space instead of signal 
  2301                              <1> 	;	    response byte address. (TRDOS 386 kernel will
  2302                              <1> 	;	    direct the cpu to that address -in user's space-
  2303                              <1> 	;	    at the return of system call or interrupt 
  2304                              <1> 	;	    just after the adjusted count/time is elapsed.)
  2305                              <1> 	;	    User's sevice routine must be ended with a
  2306                              <1> 	;	    'iret'. Normal return addresses from system 
  2307                              <1> 	;	    calls or and interrupts will be kept same except
  2308                              <1> 	;	    the timer returns. 			
  2309                              <1>      	;
  2310                              <1> 	;	BH = 0 -> Stop timer event
  2311                              <1> 	;	BL = Timer event number (1 to 255) if BH = 0     	
  2312                              <1> 	;	     If BL = 0, all timer events (which are belongs
  2313                              <1> 	;	      to running process) will be stopped 		    
  2314                              <1> 	;	ECX = Time/Tick count (depending on time count unit)
  2315                              <1> 	;	EDX = Signal return (Response) byte address
  2316                              <1> 	;	      (virtual address in user's memory space)
  2317                              <1> 	; OUTPUT ->
  2318                              <1> 	;	AL = Timer event number	(1 to 255) (max. value = 16)
  2319                              <1> 	;	IF BH Input = 0 & CF = 0 & AL = 0 -> 
  2320                              <1> 	;	     timer event(s) has/have been stopped/finished
  2321                              <1> 	;	CF = 1 & AL = 0 -> no timer setting space to set
  2322                              <1> 	;	CF = 1 & AL > 0 -> timer count unit is not usable
  2323                              <1> 	;
  2324                              <1> 	;	NOTE: To modify a time count for a user function,
  2325                              <1> 	;	      at first, current timer event must be stopped
  2326                              <1> 	;	      then a new timer event (which is related with
  2327                              <1> 	;	      same user function) must be started.
  2328                              <1> 	;		
  2329                              <1> 	;	      Signal return (response) byte may be used for 
  2330                              <1> 	;	      several purposes. Kernel will put this value 
  2331                              <1> 	;	      to requested address during timer interrupt,
  2332                              <1> 	;	      program/user can check this value to understand
  2333                              <1> 	;	      which event has been occurred and what is changed.
  2334                              <1> 	;	      (Multi timer events can share same signal address)
  2335                              <1> 	;	
  2336                              <1> 	;	NOTE: If the process is running while the time count
  2337                              <1> 	;	      is reached, kernel will put signal return (response)
  2338                              <1> 	;	      byte value at requested address during timer
  2339                              <1> 	;	      interrupt and the process will continue to run.
  2340                              <1> 	;	      Program/process must call (jump to) it's timer event
  2341                              <1> 	;	      function as required, for checking the timer event
  2342                              <1> 	;	      status via signal return (response) byte address. 
  2343                              <1> 	;
  2344                              <1> 	;	      If the process is not running (waiting or sleeping
  2345                              <1> 	;	      or released) while the time count is reached,
  2346                              <1> 	;	      it is restarted from where it left, to ensure
  2347                              <1> 	;	      proper multi media (video, audio, clock, timer)
  2348                              <1> 	;	      functionality.
  2349                              <1> 	;
  2350                              <1> 	;	      (It is better to use 'syswait' or 'syssleep',
  2351                              <1> 	;	      or 'sysrele' system call just after the timer
  2352                              <1> 	;	      function. Otherwise, timer events may block other
  2353                              <1> 	;	      processes which are not using timer events.)  	 		 			 		 	
  2354                              <1> 	;	     	      		 			
  2355                              <1> 	; Timer Event Structure: (max. 16 timer events, 16*16 bytes)
  2356                              <1> 	;       Owner:	        resb 1 ; 0 = free
  2357                              <1> 	;		  	       ;>0 = process number (u.uno)
  2358                              <1> 	;	Calback:	resb 1 ; 1 = callback, 0 = response byte
  2359                              <1> 	;	Interrupt:      resb 1 ; 0 = Timer interrupt (or none)
  2360                              <1> 	;		   	       ; 1 = Real Time Clock interrupt 
  2361                              <1> 	;	Response:       resb 1 ; 0 to 255, signal return value
  2362                              <1> 	;	Count Limit:	resd 1 ; count of ticks (total/set)
  2363                              <1> 	;	Current Count: 	resd 1 ; count of ticks (current)
  2364                              <1> 	;	Response Addr:  resd 1 ; response byte (pointer) address
  2365                              <1> 	;
  2366                              <1> 
  2367                              <1> 	; 19/12/2016 (timer callback)
  2368 0000D7F8 C605[50700100]00    <1> 	mov	byte [tcallback], 0 
  2369 0000D7FF C605[51700100]00    <1> 	mov	byte [trtc], 0
  2370 0000D806 C705[D0030300]0000- <1> 	mov	dword [u.tcb], 0 ; this is not necessary...
  2370 0000D80E 0000                <1>
  2371                              <1> 
  2372 0000D810 80FF80              <1> 	cmp	bh, 80h
  2373 0000D813 7225                <1> 	jb	short systimer_cb2
  2374 0000D815 7704                <1> 	ja	short systimer_cb0
  2375                              <1> 
  2376 0000D817 31D2                <1> 	xor	edx, edx ; 0, reset callback address
  2377 0000D819 EB0B                <1> 	jmp	short systimer_cb1
  2378                              <1> 
  2379                              <1> systimer_cb0:
  2380 0000D81B 80FF84              <1> 	cmp	bh, 84h	
  2381 0000D81E 7764                <1> 	ja	short systimer_5 ;  undefined, error
  2382                              <1> 
  2383                              <1> 	;mov	byte [tcallback], 1 ; 19/12/2016
  2384 0000D820 FE05[50700100]      <1> 	inc	byte [tcallback]
  2385                              <1> 
  2386                              <1> systimer_cb1:
  2387 0000D826 0FB635[B3030300]    <1> 	movzx	esi, byte [u.uno] ; process number
  2388 0000D82D 66C1E602            <1> 	shl	si, 2	
  2389 0000D831 8996[0C010300]      <1> 	mov	[esi+p.tcb-4], edx ; set process timer callback address
  2390                              <1> 				   ; (overwrite prev value if it is set!)
  2391 0000D837 80E77F              <1> 	and	bh, 7Fh
  2392                              <1> 
  2393                              <1> systimer_cb2:
  2394 0000D83A 80FF02              <1> 	cmp	bh, 2
  2395 0000D83D 7445                <1>         je      short systimer_5  ; only 18.2 ticks per second is usable
  2396                              <1> 				  ; 10 milliseconds (100 Hertz) timer 
  2397                              <1> 				  ; will be set later (18/05/2016)
  2398 0000D83F 774B                <1>         ja      short systimer_6 
  2399                              <1> 
  2400 0000D841 20FF                <1> 	and	bh, bh
  2401 0000D843 0F84BA000000        <1>         jz      systimer_9        ; stop timer event(s)
  2402                              <1> 
  2403                              <1> 	; bh = 1 (timer interrupt, 18.2 Hz, IBM PC/AT ROMBIOS default)
  2404                              <1> 
  2405                              <1> systimer_19:
  2406 0000D849 B00A                <1> 	mov	al, 10 ; (*)
  2407                              <1> 
  2408                              <1> systimer_0:
  2409 0000D84B B710                <1> 	mov	bh, 16
  2410                              <1> 	;
  2411 0000D84D 383D[136B0100]      <1> 	cmp	[timer_events], bh ; 16 ; 07/06/2016
  2412 0000D853 7319                <1> 	jnb 	short systimer_3  ; max. 16 timer events
  2413                              <1> 	;
  2414 0000D855 50                  <1> 	push	eax ; (*)
  2415                              <1> 
  2416 0000D856 BF[60040300]        <1> 	mov	edi, timer_set  ; beginning address of timer events
  2417                              <1> 				; setting space
  2418 0000D85B 30C0                <1> 	xor	al, al ; 0
  2419                              <1> systimer_1:
  2420 0000D85D FEC0                <1> 	inc	al
  2421 0000D85F 803F00              <1> 	cmp	byte [edi], 0 	; is it free space ?
  2422 0000D862 7639                <1> 	jna	short systimer_7 ; yes
  2423 0000D864 FECF                <1> 	dec	bh
  2424 0000D866 7405                <1> 	jz	short systimer_2
  2425 0000D868 83C710              <1> 	add	edi, 16
  2426 0000D86B EBF0                <1> 	jmp	short  systimer_1 ; next event space
  2427                              <1> 
  2428                              <1> systimer_2:
  2429 0000D86D 58                  <1> 	pop	eax ; (*) discard
  2430                              <1> systimer_3:
  2431 0000D86E C605[64030300]00    <1> 	mov	byte [u.r0], 0
  2432                              <1> systimer_4:
  2433 0000D875 C705[C8030300]1B00- <1>         mov     dword [u.error], ERR_MISC
  2433 0000D87D 0000                <1>
  2434                              <1>                                 ; one of miscellaneous/other errors
  2435 0000D87F E9F6F6FFFF          <1> 	jmp	error ; cf -> 1
  2436                              <1> 
  2437                              <1> systimer_5:
  2438 0000D884 883D[64030300]      <1> 	mov	[u.r0], bh ; Time count unit (=2 or >3)
  2439 0000D88A EBE9                <1> 	jmp	short systimer_4 ; 07/06/2016
  2440                              <1> 
  2441                              <1> systimer_6:
  2442 0000D88C 80FF04              <1> 	cmp	bh, 4
  2443 0000D88F 77F3                <1>         ja      short systimer_5  ; undefined time count unit
  2444                              <1> 	;jb	short systimer_16	
  2445                              <1> 
  2446                              <1> 	;mov	al, 1	; default (use current timer unit)
  2447                              <1> 			; countdown value is in ECX ! 
  2448                              <1> 			; max. value of ecx = 4294967296/10
  2449                              <1>         ;jmp    short systimer_0
  2450                              <1> 	;jmp	short systimer_19	
  2451 0000D891 74B6                <1> 	je	short systimer_19
  2452                              <1> 
  2453                              <1> systimer_16:
  2454                              <1> 	; bh = 3
  2455                              <1> 	; timer event via real time clock interrupt
  2456                              <1> 	; interrupt/update frequency: 1 Hz (1 tick per second)
  2457                              <1> 	
  2458 0000D893 B0B6                <1> 	mov	al, 182 ; (*) ; 18.2 * 10
  2459 0000D895 FE05[51700100]      <1> 	inc	byte [trtc] ; timer event via real time clock
  2460 0000D89B EBAE                <1>         jmp     short systimer_0
  2461                              <1> 
  2462                              <1> systimer_7:
  2463 0000D89D A2[64030300]        <1> 	mov	[u.r0], al ; timer event number
  2464                              <1> 	;
  2465                              <1> 	; edi = address of empty timer event area
  2466 0000D8A2 A0[B3030300]        <1> 	mov	al, [u.uno]
  2467 0000D8A7 FA                  <1> 	cli 	; disable interrupts 
  2468 0000D8A8 AA                  <1> 	stosb	; process number
  2469 0000D8A9 A0[50700100]        <1> 	mov	al, [tcallback] ; timer callback flag
  2470 0000D8AE AA                  <1> 	stosb 	; 1= callback method, 0= signal response byte method
  2471 0000D8AF A0[51700100]        <1> 	mov	al, [trtc] ; timer interrupt type
  2472 0000D8B4 AA                  <1> 	stosb	; 1= real time clock, 0= programmable interval timer
  2473 0000D8B5 88D8                <1> 	mov	al, bl ; Signal return (Response) value
  2474 0000D8B7 AA                  <1> 	stosb   ; response byte
  2475 0000D8B8 58                  <1> 	pop	eax ; (*) ; 10 or 182
  2476 0000D8B9 89D3                <1> 	mov	ebx, edx ; virtual address for response/signal byte
  2477 0000D8BB F7E1                <1> 	mul	ecx
  2478                              <1> 	; (eax = 10 * count of 18.2 Hz timer ticks)
  2479                              <1> 	; (count down step = 10)
  2480 0000D8BD AB                  <1> 	stosd  ; count limit (reset value)
  2481 0000D8BE AB                  <1> 	stosd  ; current count value
  2482                              <1> 
  2483                              <1> 	; 19/12/2016
  2484 0000D8BF 803D[50700100]00    <1> 	cmp	byte [tcallback], 0 ; timer callback method ?
  2485 0000D8C6 7604                <1> 	jna	short systimer_17 ; no	
  2486 0000D8C8 89D8                <1> 	mov	eax, ebx ; virtual address for callback routine 
  2487 0000D8CA EB0D                <1> 	jmp	short systimer_18
  2488                              <1> 
  2489                              <1> systimer_17: ; signal response byte method
  2490                              <1> 	; ebx = virtual address
  2491                              <1> 	; [u.pgdir] = page directory's physical address
  2492                              <1> 	; 20/02/2017
  2493 0000D8CC FE05[52700100]      <1> 	inc	 byte [no_page_swap] ; 1 
  2494                              <1> 			; Do not add this page to swap queue
  2495                              <1> 			; and remove it from swap queue if it is
  2496                              <1> 			; on the queue.
  2497 0000D8D2 E82381FFFF          <1> 	call	get_physical_addr
  2498 0000D8D7 721A                <1> 	jc	short systimer_8 ; 07/06/2016
  2499                              <1> 	; eax = physical address of the virtual address in user's space
  2500                              <1> systimer_18:
  2501 0000D8D9 AB                  <1> 	stosd	; response addr (physical) or callback addr (virtual)
  2502 0000D8DA FE05[136B0100]      <1> 	inc	byte [timer_events] ; 07/06/201
  2503                              <1> 	; 02/01/2017
  2504 0000D8E0 0FB605[B3030300]    <1> 	movzx	eax, byte [u.uno]
  2505 0000D8E7 FE80[FF000300]      <1> 	inc	byte [eax+p.timer-1]	
  2506                              <1> 	;
  2507 0000D8ED FB                  <1> 	sti 	; enable interrupts
  2508 0000D8EE E9A7F6FFFF          <1> 	jmp	sysret
  2509                              <1> 
  2510                              <1> systimer_8:
  2511                              <1> 	; 10/06/2016
  2512                              <1> 	; 07/06/2016
  2513 0000D8F3 28C0                <1> 	sub	al, al ; 0
  2514 0000D8F5 8847F4              <1> 	mov	[edi-12], al ; clear process number (free timer event)
  2515                              <1> 	;mov	dword [edi], eax ; 0
  2516 0000D8F8 FB                  <1> 	sti
  2517 0000D8F9 A2[64030300]        <1> 	mov	[u.r0], al ; 0
  2518 0000D8FE E977F6FFFF          <1> 	jmp	error
  2519                              <1> 
  2520                              <1> systimer_9:
  2521                              <1> 	; 10/06/2016
  2522                              <1> 	; 07/06/2016
  2523 0000D903 28C0                <1> 	sub	al, al
  2524 0000D905 A2[64030300]        <1> 	mov	byte [u.r0], al ; 0
  2525 0000D90A 3805[136B0100]      <1> 	cmp     byte [timer_events], al ;  0
  2526 0000D910 7631                <1> 	jna	short systimer_12
  2527                              <1> 
  2528                              <1> 	; Note: ecx and edx are undefined here
  2529                              <1> 	;	(for stop timer function)
  2530                              <1> 
  2531 0000D912 BE[60040300]        <1> 	mov	esi, timer_set  ; beginning address of timer events
  2532                              <1> 				; setting space	 
  2533 0000D917 A0[B3030300]        <1> 	mov	al, [u.uno]
  2534                              <1> 	
  2535 0000D91C B710                <1> 	mov	bh, 16
  2536                              <1> 
  2537 0000D91E 08DB                <1> 	or	bl, bl
  2538 0000D920 7544                <1> 	jnz	short systimer_15
  2539                              <1> 
  2540                              <1> 	; clear timer event areas belong to current process
  2541                              <1> 	; (for stopping all timer events belong to current process) 
  2542 0000D922 FA                  <1> 	cli 	; disable interrupts
  2543                              <1> systimer_10:
  2544                              <1> 	; 10/06/2016
  2545                              <1> 	; 07/06/2016 	
  2546 0000D923 8A26                <1> 	mov	ah, [esi]
  2547 0000D925 08E4                <1> 	or	ah, ah ; 0 ?
  2548 0000D927 7411                <1> 	jz	short systimer_11
  2549 0000D929 38C4                <1> 	cmp	ah, al ; is the process number (owner) same ?
  2550 0000D92B 750D                <1>         jne     short systimer_11 ; no
  2551                              <1> 
  2552                              <1> 	;mov	byte [esi], 0
  2553 0000D92D 66C7060000          <1> 	mov	word [esi], 0 ; clear
  2554                              <1> 	;mov	dword [esi+12], 0 ; clear
  2555                              <1> 
  2556 0000D932 FE0D[136B0100]      <1> 	dec	byte [timer_events]
  2557 0000D938 7409                <1> 	jz	short systimer_12
  2558                              <1> 
  2559                              <1> systimer_11:
  2560 0000D93A FECF                <1> 	dec	bh
  2561 0000D93C 7405                <1> 	jz	short systimer_12
  2562 0000D93E 83C610              <1> 	add	esi, 16
  2563 0000D941 EBE0                <1> 	jmp	short systimer_10
  2564                              <1> 
  2565                              <1> systimer_12:
  2566 0000D943 0FB635[B3030300]    <1> 	movzx	esi, byte [u.uno]
  2567 0000D94A 08DB                <1> 	or	bl, bl ; all timer events or one timer event ?
  2568 0000D94C 740C                <1> 	jz	short systimer_13
  2569 0000D94E 8A9E[FF000300]      <1> 	mov	bl, [esi+p.timer-1]
  2570 0000D954 20DB                <1> 	and	bl, bl	; previous number of timer events for the process
  2571 0000D956 7408                <1> 	jz	short systimer_14
  2572 0000D958 FECB                <1> 	dec	bl  ; previous number of timer events for the process - 1
  2573                              <1> systimer_13:
  2574 0000D95A 889E[FF000300]      <1> 	mov	[esi+p.timer-1], bl ; 0 ; no timer events for process
  2575                              <1> systimer_14:
  2576 0000D960 FB                  <1> 	sti	; enable interrupts
  2577 0000D961 E934F6FFFF          <1> 	jmp	sysret
  2578                              <1> 
  2579                              <1> systimer_15:
  2580 0000D966 38FB                <1> 	cmp	bl, bh ; 16
  2581 0000D968 0F8707FFFFFF        <1>         ja      systimer_4      ; max. 16 timer events !
  2582                              <1> 	;
  2583 0000D96E 88DA                <1> 	mov	dl, bl
  2584 0000D970 FECA                <1> 	dec	dl  ; 16 -> 15 ... 1 -> 0 
  2585 0000D972 C0E204              <1> 	shl	dl, 4 ; * 16
  2586 0000D975 0FB6FA              <1> 	movzx	edi, dl
  2587 0000D978 01F7                <1> 	add	edi, esi ; timer_set 
  2588                              <1> 	
  2589 0000D97A 3A07                <1> 	cmp	al, [edi] ; process number
  2590 0000D97C 0F85F3FEFFFF        <1>         jne     systimer_4
  2591                              <1> 	
  2592                              <1> 	; same process ID
  2593 0000D982 FA                  <1> 	cli	; disable interrupts
  2594                              <1>  	; 10/06/2016 ; 02/01/2017
  2595                              <1> 	;mov	byte [edi], 0 
  2596 0000D983 66C7070000          <1> 	mov	word [edi], 0 ; clear
  2597                              <1> 	;mov	dword [edi+12], 0 ; clear
  2598 0000D988 FE0D[136B0100]      <1> 	dec	byte [timer_events]
  2599 0000D98E EBB3                <1> 	jmp	short systimer_12
  2600                              <1> 
  2601                              <1> sysvideo: ; VIDEO DATA TRANSFER FUNCTIONS
  2602                              <1> 	; 23/11/2020
  2603                              <1> 	; 22/11/2020
  2604                              <1> 	; 21/11/2020 (TRDOS 386 v2.0.3)
  2605                              <1> 	; 12/05/2017
  2606                              <1> 	; 11/07/2016
  2607                              <1> 	; 13/06/2016
  2608                              <1> 	; 16/05/2016 - TRDOS 386 (TRDOS v2.0)
  2609                              <1> 	;
  2610                              <1> 	; VIDEO DATA TRANSFER FUNCTIONS:
  2611                              <1> 	;
  2612                              <1> 	; Inputs:
  2613                              <1> 	;	BH = 0 = VIDEO BIOS Mode 3, tty/text mode data transfers
  2614                              <1> 	;	     BL = 
  2615                              <1> 	;		Bits 0&1, Transfer direction
  2616                              <1> 	;	     	 	0 - System to system
  2617                              <1> 	;			1 - User to system
  2618                              <1> 	;			2 - System to user
  2619                              <1> 	;			3 - User to user (undefined)
  2620                              <1> 	;		Bits 2&3, Transfer Type
  2621                              <1> 	;			0 - Display page transfer	
  2622                              <1> 	;	     		1 - Display page window transfer
  2623                              <1> 	;	     		2 - Frame/Viewport/Window address transfer
  2624                              <1> 	;			3 - Window handle transfer (undefined)
  2625                              <1> 	;		; 23/11/2020
  2626                              <1> 	;		Bits 4..7 - Reserved, undefined (must be 0)
  2627                              <1> 	;
  2628                              <1> 	;	     /// BL = 0 -> System to system (display page) transfer
  2629                              <1> 	;		 CL = Source page 
  2630                              <1> 	;		 DL = Destination page
  2631                              <1> 	;	     /// BL = 1&2 -> user to system & system to user transfer
  2632                              <1> 	;		 ECX = User' buffer address
  2633                              <1> 	;		 DL = Video page
  2634                              <1> 	;	     /// BL = 5&6 -> user to system, system to user transfer 
  2635                              <1> 	;		(system window is in current/active display page)	 	 		
  2636                              <1> 	;		 ESI = User's buffer address
  2637                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2638                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2639                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2640                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2641                              <1>         ;                If BL = 5 ->
  2642                              <1> 	;		 EDI = Swap address (in user's memory space)
  2643                              <1> 	;		 (If swap address > 0, previous content of the window
  2644                              <1> 	;		 will be saved into swap area in user's memory space)		
  2645                              <1> 	;	     /// BL = 4 -> system to system transfer
  2646                              <1> 	;		 ESI = System's source buffer (video page) address
  2647                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2648                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2649                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2650                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2651                              <1> 	;		 EDI = System's destination buffer (video page) address
  2652                              <1> 	;		; 22/11/2020
  2653                              <1> 	;	     /// BL = 9&10 -> user to system, system to user transfer 
  2654                              <1> 	;		(system window is in current/active display page)	 	 		
  2655                              <1> 	;		 ESI = User's buffer address
  2656                              <1> 	;		  CX = offset in video page (char position in 80*25)
  2657                              <1> 	;		  DX = transfer count (character count, max. 80*25)
  2658                              <1>         ;                If BL = 5 ->
  2659                              <1> 	;		 EDI = Swap address (in user's memory space)
  2660                              <1> 	;		 (If swap address > 0, previous content of the window
  2661                              <1> 	;		 will be saved into swap area in user's memory space)	
  2662                              <1> 	;	     /// BL = 8 -> system to system transfer
  2663                              <1> 	;		 ESI = System's source buffer (video page) address
  2664                              <1> 	;		  CX = offset in video page (char position in 80*25)
  2665                              <1> 	;		  DX = transfer count (character count, max. 80*25)
  2666                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2667                              <1> 	;		 EDI = System's destination buffer (video page) address
  2668                              <1> 	;
  2669                              <1> 	;		; 23/11/2020 (major modification)
  2670                              <1> 	;		; 22/11/2020 (bugfixes and extensions)
  2671                              <1> 	;	BH = 1 = VGA Graphics (0A0000h) data transfers
  2672                              <1> 	;	     BL = 
  2673                              <1> 	;	     	x0h = Fill color (color in CL) (64K)
  2674                              <1> 	;		x1h = User to system display page transfer
  2675                              <1> 	;		x2h = System to user display page transfer
  2676                              <1> 	;		x3h = NOT bits in window (ECX, EDX)
  2677                              <1> 	;		x4h = Window copy (system to system)	
  2678                              <1> 	;	     	x5h = User to system window transfer
  2679                              <1> 	;	     	x6h = System to user window transfer
  2680                              <1> 	;		x7h = AND display page bytes with CL
  2681                              <1> 	;		x8h = OR display page bytes with CL
  2682                              <1> 	;		x9h = XOR display page bytes with CL
  2683                              <1> 	;		; 22/11/2020 (TRDOS v2.0.3)
  2684                              <1> 	;	        xAh = INC display page bytes
  2685                              <1> 	;	        xBh = DEC display page bytes
  2686                              <1> 	;	        xCh = NEG display page bytes
  2687                              <1> 	;	        xDh = NOT display page bytes
  2688                              <1> 	;
  2689                              <1> 	;		x = 0 -> screen width = 320
  2690                              <1> 	;		x = 1 -> screen width = 640
  2691                              <1> 	;		x = 2 -> screen width = 800
  2692                              <1> 	;
  2693                              <1> 	;	     /// BL = 0 -> Fill color (all screen pixels)
  2694                              <1> 	;		 CL = Color value, 
  2695                              <1> 	;		 If CH > 0, color in CL will be mixed with pixel color  
  2696                              <1> 	;	     /// BL = 1&2 -> user to system & system to user transfer
  2697                              <1> 	;		 ECX = User buffer
  2698                              <1> 	;	     /// BL = 5&6 -> user to system, system to user transfer 
  2699                              <1> 	;		(window in current display page and in current mode)		 		
  2700                              <1> 	;		 ESI = User's buffer address
  2701                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2702                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2703                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2704                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2705                              <1>        	;	     /// BL = 4 -> system to system (window) transfer 
  2706                              <1> 	;		 ESI = System's source buffer (video page) address
  2707                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2708                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2709                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2710                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2711                              <1> 	;		 EDI = System's destination buffer (video page) address
  2712                              <1> 	;	     /// BL = 3 -> NOT byte in display page/memory 
  2713                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2714                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2715                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2716                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2717                              <1> 	;
  2718                              <1> 	;	BH = 2 = Super VGA, LINEAR FRAME BUFFER data transfers
  2719                              <1> 	;	     BL = 
  2720                              <1> 	;	     	0 = Fill color (color in ECX) (Frame buffer size)
  2721                              <1> 	;		1 = User to system display page transfer
  2722                              <1> 	;		2 = System to user display page transfer
  2723                              <1> 	;		3 = NOT bits in window (ECX, EDX)
  2724                              <1> 	;		4 = Window copy (system to system)	
  2725                              <1> 	;	     	5 = User to system window transfer
  2726                              <1> 	;	     	6 = System to user window transfer
  2727                              <1> 	;		7 = AND display page bytes with ECX
  2728                              <1> 	;		8 = OR display page bytes with ECX
  2729                              <1> 	;		9 = XOR display page bytes with ECX
  2730                              <1> 	;		; 22/11/2020 (TRDOS v2.0.3)
  2731                              <1> 	;	       10 = INC display page bytes (color mask in CL) 
  2732                              <1> 	;	       11 = DEC display page bytes (color mask in CL)
  2733                              <1> 	;	       12 = NEG display page bytes (color mask in CL)
  2734                              <1> 	;	       13 = NOT display page bytes (color mask in CL)
  2735                              <1> 	;
  2736                              <1> 	;	     /// BL = 0 -> Fill color (all screen pixels)
  2737                              <1> 	;		 CL = Color value, 
  2738                              <1> 	;		 If CH > 0, color in CL will be mixed with pixel color 
  2739                              <1> 	;	     /// BL = 1&2 -> user to system & system to user transfer
  2740                              <1> 	;		 ECX = User buffer
  2741                              <1> 	;	     /// BL = 5&6 -> user to system, system to user transfer 
  2742                              <1> 	;		(window in current display page and in current mode)	 	 		
  2743                              <1> 	;		 ESI = User's buffer address
  2744                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2745                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2746                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2747                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2748                              <1> 	;	     /// BL = 4 -> system to system (window) transfer 
  2749                              <1> 	;		 ESI = System's source buffer (video page) address
  2750                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2751                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2752                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2753                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2754                              <1> 	;		 EDI = System's destination buffer (video page) address
  2755                              <1> 	;	     /// BL = 3 -> NOT byte in display page/memory 
  2756                              <1> 	;		 ECX Low 16 bits = Top left column (X1 position)
  2757                              <1> 	;		 ECX High 16 bits = Top row (Y1 position)
  2758                              <1> 	;		 EDX Low 16 bits = Bottom right column (X2 position)
  2759                              <1> 	;		 EDX High 16 bits = Bottom row (Y2 position)
  2760                              <1> 	;
  2761                              <1> 	;		Example: (21/11/2020)
  2762                              <1> 	;			esi = 0B0000h (window start value)
  2763                              <1> 	;			ecx = 00000000h (start at row 0, column 0) 
  2764                              <1> 	;			edx = 0018004Fh (end at row 24,column 79)
  2765                              <1> 	;			row count= 25, column count = 80
  2766                              <1> 	;			(end) byte offset = (80*2)*24+(79*2) = 3998	
  2767                              <1> 	;			end value of esi = 0B8F9Eh (last word of page)
  2768                              <1> 	;			(! end address is included to transfer !)
  2769                              <1> 	;			((just as line start and line end coordinates)) 
  2770                              <1> 	;
  2771                              <1> 	; Outputs:
  2772                              <1> 	;	EAX = transfer/byte count
  2773                              <1> 	;
  2774                              <1> 	;	NOTE: If the source or destination address passes out of
  2775                              <1> 	;	video pages (display memory limits), data will not be transferred
  2776                              <1> 	;	and EAX will return as 0.
  2777                              <1> 	;
  2778                              <1> 	; PIXEL READ/WRITE
  2779                              <1> 	;
  2780                              <1> 	;	BH = 3 = Read/Write pixel(s) -for all graphics modes-
  2781                              <1> 	;	     BL = 
  2782                              <1> 	;	     bits 0&1&2
  2783                              <1> 	;		0 = Read one pixel
  2784                              <1> 	;		1 = Write one pixel
  2785                              <1> 	;	     	2 = Read two pixels
  2786                              <1> 	;		3 = Write two pixels
  2787                              <1> 	;	     	4 = Read four pixels
  2788                              <1> 	;		5 = Write four pixels
  2789                              <1> 	;		6 - read one nibble (4 bits)
  2790                              <1> 	;		7 - write one nibble (4 bits)
  2791                              <1> 	;	     bit 3 - color mix option (1 = mix, 0 = overwrite)
  2792                              <1> 	;	     bit 4 - true color (dword color number) option
  2793                              <1> 	;		   (linear frame buffer address will be used)
  2794                              <1> 	;	     bit 5 - alpha byte will be written if bit 5 is 1			 	
  2795                              <1> 	;	     bit 6 - use CL if bit 6 is set (do not use ECX or CX)
  2796                              <1> 	;	     bit 7 - force/use linear frame buffer address
  2797                              <1> 	;		    (if bit 7&4 are 0, 0A0000h address will be used)		
  2798                              <1> 	;		
  2799                              <1> 	;	     CL = color for writing pixel(s) or
  2800                              <1>  	;	     ECX = color for writing pixel(s) in true color modes
  2801                              <1> 	;		  or ecx is used as separate color bytes for reading
  2802                              <1> 	;		  or writing 2 or 4 pixels in byte order
  2803                              <1> 	;		 (24 bit will be written for 24 bit true color modes)
  2804                              <1> 	;		 (alpha byte will be regarded for 32 bit true colors)
  2805                              <1> 	;		 (but alpha byte will not written if BL bit 5 is 0)
  2806                              <1> 	;
  2807                              <1> 	;	     EDX = Offset from start of video memory (0A0000h)
  2808                              <1> 	;		   or start of linear frame buffer
  2809                              <1> 	;		  (edx contains nibble offset if BL bits 1&2 are 1)
  2810                              <1> 	;		  (nibble read/write is used with low 4 bits of CL) 
  2811                              <1> 	;
  2812                              <1> 	; Outputs:
  2813                              <1> 	;	EAX = pixel color (according to BL and CL input)
  2814                              <1> 	;	
  2815                              <1> 	;
  2816                              <1> 	; DIRECT (STANDARD VGA/CGA) DISPLAY MEMORY ACCESS FUNCTIONS:
  2817                              <1> 	;
  2818                              <1> 	;	BH = 4 = CGA direct video memory (0B8000h, 32K) access
  2819                              <1> 	;		Page directory & page tables of the user's
  2820                              <1> 	;		program will be updated to direct access to
  2821                              <1> 	;		0B8000h (32K) video (CGA, color) memory; if
  2822                              <1> 	;		there is not a permission conflict or lock!  
  2823                              <1> 	;	        (User's program/process will have permission to
  2824                              <1> 	;		access locked display memory if the owner is
  2825                              <1> 	;		it's parent.)
  2826                              <1>         ;
  2827                              <1> 	;	    Screen width = 320	
  2828                              <1> 	;
  2829                              <1> 	;	BH = 5 = VGA direct video memory (0A0000h, 64K) access
  2830                              <1> 	;		Page directory & page tables of the user's
  2831                              <1> 	;		program will be updated to direct access to
  2832                              <1> 	;		0A0000h (64K) video (VGA) memory; if there is not
  2833                              <1> 	;		a permission conflict or lock!  
  2834                              <1> 	;	        (User's program/process will have permission to
  2835                              <1> 	;		access locked display memory if the owner is
  2836                              <1> 	;		it's parent.)
  2837                              <1> 	;	
  2838                              <1> 	;	    ; 23/11/2020		
  2839                              <1> 	;	    Screen width options = 320, 640, 800 
  2840                              <1> 	;			
  2841                              <1> 	; Outputs:
  2842                              <1> 	;	EAX = Display memory address for direct access
  2843                              <1> 	;	      0A0000h for VGA, 0B8000h for CGA	
  2844                              <1> 	;	(Display memory size: 32K for CGA, 64K for VGA)
  2845                              <1> 	; 	EAX = 0 if display page access permission has been denied. 
  2846                              <1> 	;	      (Locked!) 	
  2847                              <1> 	;	      	 	
  2848                              <1> 	; LINEAR FRAME BUFFER ACCESS FUNCTIONS:
  2849                              <1> 	;
  2850                              <1> 	;	BH = 6 = Linear Frame Buffer direct video memory access
  2851                              <1> 	;
  2852                              <1> 	;		Page directory & page tables of the user's
  2853                              <1> 	;		program will be updated to direct access to
  2854                              <1> 	;		the configured LFB (Linear Frame Buffer) address,
  2855                              <1> 	;		if there is not a permission conflict or lock!  
  2856                              <1> 	;	        (User's program/process will have permission to
  2857                              <1> 	;		access locked display memory if the owner is
  2858                              <1> 	;		it's parent.)
  2859                              <1> 	;			
  2860                              <1> 	;		Return: EAX = Linear Frame Buffer address
  2861                              <1> 	;			EDX = Frame Buffer Size in bytes	
  2862                              <1> 	;
  2863                              <1> 	; 	23/11/2020
  2864                              <1> 	; ***	GET VIDEO MODE & LINEAR FRAME BUFFER INFO   
  2865                              <1> 	;	(This function -7- also is used for VGA and CGA modes)
  2866                              <1> 	; 	
  2867                              <1> 	;	BH = 7 = Get Linear Frame Buffer info (for current mode)
  2868                              <1> 	;		
  2869                              <1> 	;		Return:
  2870                              <1> 	;		EAX = Frame Buffer Address (0 = is not in use)
  2871                              <1> 	;		EDX = Frame Buffer Size in bytes
  2872                              <1> 	;		 BX = Current Video Mode (VGA bios modes)
  2873                              <1> 	;		      If BH = 1 ->
  2874                              <1> 	;			 BX = VESA VBE2 extended video mode
  2875                              <1> 	;		      If BH = 0FFh (if BL input is 0FFh)
  2876                              <1> 	;			 BL = 0 - 256 virtual colors (of 16M)	
  2877                              <1> 	;			      1 - 16 colors
  2878                              <1> 	;		     	      2 - 256 colors
  2879                              <1> 	;		     	      3 - 65536 colors
  2880                              <1> 	;			      4 - 24 bit true colors (16M colors)
  2881                              <1> 	;		     	      5 - 32 bit true colors (16M colors)
  2882                              <1> 	;		     	      6 - mono color (black-white)
  2883                              <1> 	;		     	      7 - 4 colors
  2884                              <1> 	;		Note:	
  2885                              <1> 	;		Alpha byte will be used as virtual color index.
  2886                              <1> 	;		(32 bit pixel colors.. byte 0,1,2 rgb and 3 alpha)
  2887                              <1> 	;
  2888                              <1> 	;		ECX = Pixel resolution
  2889                              <1> 	;		      CX = Width (320, 640, 800, 1024, 1366, 1920)
  2890                              <1> 	;		      High 16 bits of ECX = Height  
  2891                              <1> 	;
  2892                              <1> 	;	NOTE: Each process will have it's own frame buffer
  2893                              <1> 	;	      address and resolution parameters in 'u' area.
  2894                              <1> 	;	      Then, if the current frame buffer & resolution
  2895                              <1> 	;	      is different, frame buffer r/w functions
  2896                              <1> 	;	      will use scale factor to convert process's
  2897                              <1>         ;             pixel coordinates to actual screen coordinates.                            
  2898                              <1> 	;	      resolution -> dimensional scale
  2899                              <1> 	;	      color size -> color scale
  2900                              <1> 	;	     * RGB (TRUE) colors to 256 colors conversion:	
  2901                              <1>         ;             TRUE Colors -> 8,8,8 (R,G,B; byte 0 is R)            
  2902                              <1> 	;	      256 colors -> 2,2,2,2 (R,G,B,L; bit 0&1 is R)
  2903                              <1> 	; 		  bit 6&7 -> luminosity base level (0,1,2,3)
  2904                              <1> 	;		  bit 4&5 -> blue level (0,1,2,3)
  2905                              <1> 	;		  bit 2%3 -> green level (0,1,2,3)
  2906                              <1> 	;		  bit 0&1 -> red level (0,1,2,3)
  2907                              <1> 	;	      Example: total red level : luminosity + red level   				
  2908                              <1> 	;	      Luminosity base level: 0 -> 16
  2909                              <1> 	;		 		     1 -> 32
  2910                              <1> 	;				     2 -> 64
  2911                              <1> 	;				     3 -> 128
  2912                              <1> 	;	      Color level:	
  2913                              <1> 	;				    0 -> 0
  2914                              <1> 	;				    1 -> luminosity level
  2915                              <1> 	;				    2 -> luminosity level + 64
  2916                              <1> 	;				    3 -> 255
  2917                              <1> 	;	     Luminosity base level = min (R,G,B)
  2918                              <1> 	;			if it is <16, it will be set to 16
  2919                              <1> 	;	     Color levels: Color values are fixed to (nearest) 
  2920                              <1> 	;		   one of all possible set level (step) values
  2921                              <1> 	;		   (according to luminosity base level); then
  2922                              <1> 	;		   color levels are set to R-L, G-L, B-L.
  2923                              <1> 	;	 For example: If luminosity base level is 32
  2924                              <1> 	;		  all possible set values are 0, 32, 96, 255. 	 			
  2925                              <1> 	;
  2926                              <1> 	;	    * RGB (TRUE) colors to 16 colors conversion:
  2927                              <1> 	;	    16 colors: R,B,G,L bits (4 bits)
  2928                              <1> 	;	    	   If any one of R,G,B >= 128 L = 1 		     	
  2929                              <1>  	;		   If max. value of (R,G,B) >= 32, it is 1
  2930                              <1> 	;		      else all color bits (R&G&B&L) are 0
  2931                              <1> 	;		   If the second value >= max. value / 2
  2932                              <1> 	;		      it is 1
  2933                              <1> 	;		   If third value value >= max. value / 2
  2934                              <1> 	;		      it is 1
  2935                              <1> 	;	    Example: R = 132, G = 64, B = 78
  2936                              <1> 	;		     L = 1, R = 1
  2937                              <1> 	;		     G < 66 --> G = 0
  2938                              <1> 	;		     B >= 66 --> B = 1
  2939                              <1> 	;
  2940                              <1> 	; 	23/11/2020
  2941                              <1> 	; SET VIDEO MODE & COLOR INDEXES (not implemented yet)
  2942                              <1> 	;	
  2943                              <1> 	;	BH = 8 = Set Video Mode & Color Indexes (256 colors)
  2944                              <1> 	;		
  2945                              <1> 	;		BL = Requested Video Mode (method)
  2946                              <1> 	;
  2947                              <1> 	;		bit 0&1 -
  2948                              <1> 	;		     0 - VGA modes
  2949                              <1> 	;		     1 - VESA (VBE2) modes
  2950                              <1> 	;		     2 - TRD0S 386 mode index
  2951                              <1> 	;		     3 - Resolution in ECX
  2952                              <1> 	;		bit 2&3&4
  2953                              <1> 	;		     0 - 256 virtual colors (of 16M colors)
  2954                              <1> 	;		     1 - 16 colors
  2955                              <1> 	;		     2 - 256 colors
  2956                              <1> 	;		     3 - 65536 colors
  2957                              <1> 	;		     4 - 24 bit true colors (16M colors)
  2958                              <1> 	;		     5 - 32 bit	true colors (16M colors)
  2959                              <1> 	;		     6 - mono color (black-white)
  2960                              <1> 	;		     7 - 4 colors
  2961                              <1> 	;		bit 5 - color palette (index) option
  2962                              <1> 	;		bit 6 - force VESA VBE 3 protected mode interface
  2963                              <1> 	;		     (set equivalent VBE mode by using 'PMID' info)
  2964                              <1> 	;		bit 7 - do not set mode, but check if available  	
  2965                              <1> 	;
  2966                              <1> 	;		ECX = Pixel resolution (if bit 0&1 of BL are 1)
  2967                              <1> 	;		      CX = Width (320, 640, 800, 1024, 1366, 1920)
  2968                              <1> 	;		      High 16 bits of ECX = Height
  2969                              <1> 	;		     (BL bit 2,3,4 is used for color option) 	
  2970                              <1> 	;		
  2971                              <1> 	;		ECX = Video mode (if bit 1 of BL is 0) 
  2972                              <1> 	;
  2973                              <1> 	;		EDX = user's true color palette buffer for
  2974                              <1> 	;		      mono, 4 colors, 16 colors, 256 colors only   
  2975                              <1> 	;		     (edx will be used if bit 5 of BL is set)
  2976                              <1> 	;		     ((True colors mode will be set but 256 virtual
  2977                              <1> 	;		     colors will be used if BL bits 2&3&4 is 0.))
  2978                              <1> 	;		Note: 
  2979                              <1> 	;		Alpha byte will be used as virtual color index.
  2980                              <1> 	;		(32 bit pixel colors.. byte 0,1,2 rgb and 3 alpha)	 	
  2981                              <1> 	;
  2982                              <1> 	;		TRDOS 386 v2 mode index (BL, bit 2%3&4)
  2983                              <1> 	;		  0 - 80x25 text, 16 colors
  2984                              <1> 	;		  1 - 320x200 graphics, 256 colors
  2985                              <1> 	;		  2 - 640x480 graphics, 256 colors		 		 	  								 	 					
  2986                              <1> 	;		  3 - 800x600 graphics, 256 colors	
  2987                              <1> 	;		  4 - 1024x768 graphics, 256 colors
  2988                              <1> 	;		  5 - 1024x768 graphics, 16M colors (24+8 bits)
  2989                              <1> 	;		  6 - 1366x768 graphics, 16M colors (24+8 bits)
  2990                              <1> 	;		  7 - 1920x1080 graphics, 16M colors (24+8 bits)
  2991                              <1> 	;		(256 colors modes can be used with color palette)
  2992                              <1> 	;
  2993                              <1> 	; Outputs:
  2994                              <1> 	;	EAX = Requested (Proper) video mode number + 1
  2995                              <1> 	;	      ("dec eax" by user will give requested video mode)	
  2996                              <1> 	;
  2997                              <1> 	;	EAX = 0 -> Error
  2998                              <1> 	;
  2999                              <1> 
  3000                              <1> 	; 16/05/2016
  3001 0000D990 31C0                <1> 	xor	eax, eax
  3002 0000D992 A3[64030300]        <1> 	mov	[u.r0], eax
  3003 0000D997 20FF                <1> 	and	bh, bh
  3004 0000D999 0F858A020000        <1> 	jnz	sysvideo_13 ; 11/07/2016
  3005                              <1> 
  3006                              <1> 	;; 21/11/2020 (TRDOS 386 v2.0.3)
  3007                              <1> 	;; tty/text mode transfers are only for video mode 3
  3008                              <1> 
  3009                              <1> 	; 22/11/2020
  3010                              <1> 	;cmp	byte [CRT_MODE], 3 ; 80x25 text, 16 colors
  3011                              <1> 	;jne	sysret ; invalid (nothing to do), [u.r0] = 0	
  3012                              <1> 	
  3013                              <1> 	; 23/11/2020
  3014                              <1> 	; bit 7,6,5,4 of BL are reserved and it must be 0
  3015                              <1> 	;	 	 for current 'sysvideo' version
  3016 0000D99F F6C3F0              <1> 	test	bl, 0F0h
  3017 0000D9A2 0F85F2F5FFFF        <1> 	jnz	sysret ; invalid (undefined) ! 
  3018                              <1> 
  3019                              <1> 	; Video mode 0, 80*25 text mode, CGA 16 colors  ; [CRT_MODE] = 3
  3020 0000D9A8 88DF                <1> 	mov	bh, bl
  3021 0000D9AA C0EF02              <1> 	shr	bh, 2 ; 4..7 -> 1, 8..11 -> 2, 12..15 -> 3
  3022                              <1> 	; 21/11/2020
  3023                              <1> 	;and	bh, bh
  3024 0000D9AD 0F8592000000        <1>         jnz	sysvideo_4  ; Display page window transfer etc.
  3025                              <1> 
  3026                              <1> 	; Display page (complete) transfer
  3027                              <1> 
  3028 0000D9B3 BF00800B00          <1> 	mov	edi, 0B8000h
  3029                              <1> 	; dl = display page number, destination
  3030 0000D9B8 66B80010            <1> 	mov	ax, 4096 ; 21/11/2020
  3031 0000D9BC 20D2                <1> 	and	dl, dl
  3032 0000D9BE 7413                <1> 	jz	short sysvideo_1
  3033 0000D9C0 80FA07              <1> 	cmp	dl, 7
  3034 0000D9C3 0F87D1F5FFFF        <1> 	ja	sysret ; invalid (nothing to do), [u.r0] = 0
  3035                              <1> sysvideo_0:
  3036                              <1> 	; page lenght = 4096 bytes (but page content is 80*25*2 bytes)
  3037 0000D9C9 81C700100000        <1> 	add	edi, 4096 ; 21//11/2020 ([CRT_LEN] = 1000h for mode 3)
  3038 0000D9CF FECA                <1> 	dec	dl
  3039 0000D9D1 75F6                <1> 	jnz	short sysvideo_0	
  3040                              <1> sysvideo_1:	
  3041 0000D9D3 80E303              <1> 	and	bl, 3
  3042 0000D9D6 752A                <1> 	jnz	short sysvideo_2 ; user to system display page transfer
  3043                              <1> 	; cl = display page number, source
  3044 0000D9D8 80F907              <1> 	cmp	cl, 7
  3045 0000D9DB 0F87B9F5FFFF        <1> 	ja	sysret ; invalid (nothing to do), [u.r0] = 0
  3046                              <1> 	; system to system video/display page transfer (mode 0)
  3047                              <1> 	; 21/11/2020
  3048                              <1> 	;mov	esi, 0B8000h
  3049                              <1> 	;movzx	eax, cl
  3050                              <1> 	;mov	edx, 4096 ; [CRT_LEN] = 1000h for video mode 3
  3051                              <1> 	;mov	ecx, edx
  3052                              <1> 	;mul	edx
  3053                              <1> 	;add	esi, eax
  3054 0000D9E1 0FB6F1              <1> 	movzx	esi, cl
  3055 0000D9E4 66C1E60C            <1> 	shl	si, 12 ; * 4096
  3056 0000D9E8 81C600800B00        <1> 	add	esi, 0B8000h 
  3057                              <1> 
  3058                              <1> 	; 21/11/2020
  3059                              <1> 	;mov	ecx, 4096
  3060 0000D9EE 89C1                <1> 	mov	ecx, eax ; 4096
  3061                              <1> 	;mov	[u.r0], ecx ; 4096 bytes
  3062 0000D9F0 66890D[64030300]    <1> 	mov	[u.r0], cx
  3063                              <1> 
  3064 0000D9F7 66C1E902            <1> 	shr	cx, 2 ; / 4
  3065 0000D9FB F3A5                <1> 	rep	movsd
  3066 0000D9FD E998F5FFFF          <1> 	jmp	sysret	
  3067                              <1> sysvideo_2:  
  3068 0000DA02 80FB02              <1> 	cmp	bl, 2
  3069 0000DA05 0F878FF5FFFF        <1>         ja      sysret; invalid (user to user), [u.r0] = 0
  3070 0000DA0B 721D                <1> 	jb	short sysvideo_3 ; user to system
  3071                              <1> 	; system to user video/display page transfer (mode 0)
  3072 0000DA0D 89FE                <1> 	mov	esi, edi
  3073 0000DA0F 89CF                <1> 	mov	edi, ecx ; user buffer
  3074                              <1> 	; 21/11/2020
  3075 0000DA11 89C1                <1> 	mov	ecx, eax ; 4096
  3076 0000DA13 E84A130000          <1> 	call	transfer_to_user_buffer ; fast transfer
  3077 0000DA18 0F827CF5FFFF        <1> 	jc	sysret ; [u.r0] = 0
  3078                              <1> 	; 21/11/2020
  3079                              <1> 	;mov	[u.r0], ecx
  3080 0000DA1E 66890D[64030300]    <1> 	mov	[u.r0], cx
  3081 0000DA25 E970F5FFFF          <1> 	jmp	sysret	
  3082                              <1> sysvideo_3: 
  3083                              <1> 	; user to system video/display page transfer (mode 0)	
  3084 0000DA2A 89CE                <1> 	mov	esi, ecx ; user buffer
  3085                              <1> 	; edi = video page address
  3086                              <1> 	; 21/11/2020
  3087 0000DA2C 89C1                <1> 	mov	ecx, eax ; 4096
  3088 0000DA2E E879130000          <1> 	call	transfer_from_user_buffer ; fast transfer
  3089 0000DA33 0F8261F5FFFF        <1> 	jc	sysret ; [u.r0] = 0
  3090                              <1> 	; 21/11/2020
  3091                              <1> 	;mov	[u.r0], ecx
  3092 0000DA39 66890D[64030300]    <1> 	mov	[u.r0], cx
  3093 0000DA40 E955F5FFFF          <1> 	jmp	sysret
  3094                              <1> 
  3095                              <1> sysvideo_4:
  3096                              <1> 	; 23/11/2020 (TRDOS 386 v2.0.3)
  3097                              <1> 
  3098                              <1> 	; Display page window transfer etc.
  3099 0000DA45 80E303              <1> 	and	bl, 3
  3100 0000DA48 0F85F7000000        <1>         jnz     sysvideo_9 ; user to system or system to user
  3101                              <1> 	; 21/11/2020
  3102                              <1> 	; system to system video/display page window transfer (mode 0)
  3103 0000DA4E 81FE00800B00        <1> 	cmp	esi, 0B8000h	; source buffer address (system)
  3104 0000DA54 0F8240F5FFFF        <1> 	jb	sysret
  3105 0000DA5A 81FE00000C00        <1> 	cmp	esi, 0B8000h+(4096*8)
  3106 0000DA60 0F8334F5FFFF        <1> 	jnb	sysret
  3107 0000DA66 81FF00800B00        <1> 	cmp	edi, 0B8000h	; destination buffer address (system)	
  3108 0000DA6C 0F8228F5FFFF        <1> 	jb	sysret
  3109 0000DA72 81FF00000C00        <1>         cmp     edi, 0B8000h+(4096*8)
  3110 0000DA78 0F831CF5FFFF        <1> 	jnb	sysret
  3111                              <1> 	;
  3112 0000DA7E 51                  <1> 	push	ecx ; X1 and Y1 position - top left column, row
  3113 0000DA7F 0FB7C1              <1> 	movzx	eax, cx ; top left column
  3114                              <1> 	; 21/11/2020
  3115 0000DA82 C1E910              <1> 	shr	ecx, 16 ; top row
  3116 0000DA85 740E                <1> 	jz	short sysvideo_4_0 ; bypass following code
  3117 0000DA87 52                  <1> 	push	edx ; X2 and Y2 position - bottom right column, row
  3118 0000DA88 50                  <1> 	push	eax
  3119 0000DA89 66B8A000            <1> 	mov	ax, 80*2 ; 80 colums, 160 bytes per row
  3120 0000DA8D F7E1                <1> 	mul	ecx
  3121                              <1> 		; eax = offset for start row number 
  3122 0000DA8F 01C6                <1> 	add	esi, eax
  3123 0000DA91 01C7                <1> 	add	edi, eax
  3124 0000DA93 58                  <1> 	pop	eax
  3125 0000DA94 5A                  <1> 	pop	edx
  3126                              <1> sysvideo_4_0:
  3127 0000DA95 66D1E0              <1> 	shl	ax, 1 ; * 2 ; convert start column number to offset
  3128 0000DA98 7404                <1> 	jz	short sysvideo_4_1	
  3129 0000DA9A 01C6                <1> 	add	esi, eax
  3130 0000DA9C 01C7                <1> 	add	edi, eax
  3131                              <1> 		; esi = source page window start offset
  3132                              <1> 		; edi = destination page window start offset
  3133                              <1> sysvideo_4_1:
  3134 0000DA9E 59                  <1> 	pop	ecx
  3135                              <1> 	;mov	eax, 0B8000h+(80*25*2*8)
  3136                              <1> 	; 21/11/2020
  3137 0000DA9F B800000C00          <1> 	mov	eax, 0B8000h+(4096*8)
  3138 0000DAA4 39C6                <1> 	cmp	esi, eax
  3139 0000DAA6 0F83EEF4FFFF        <1> 	jnb	sysret ; out of video page
  3140 0000DAAC 39C6                <1> 	cmp	esi, eax
  3141 0000DAAE 0F83E6F4FFFF        <1> 	jnb	sysret  ;out of video page	
  3142                              <1> 
  3143 0000DAB4 56                  <1> 	push	esi ; ****
  3144 0000DAB5 57                  <1> 	push	edi ; ***
  3145 0000DAB6 52                  <1> 	push	edx ; **
  3146 0000DAB7 51                  <1> 	push	ecx ; *
  3147 0000DAB8 C1E910              <1> 	shr	ecx, 16 ; top row
  3148 0000DABB C1EA10              <1> 	shr	edx, 16 ; bottom row
  3149                              <1> 	; 21/11/2020
  3150                              <1> 	;cmp	ecx, 24 ; max. 25 rows
  3151 0000DABE 6683F918            <1> 	cmp	cx, 24
  3152 0000DAC2 7778                <1> 	ja	short sysvideo_6 ; invalid, [u.r0] = 0
  3153                              <1> 	;cmp	edx, 24 ; max. 25 rows
  3154 0000DAC4 6683FA18            <1> 	cmp	dx, 24
  3155 0000DAC8 7772                <1> 	ja	short sysvideo_6 ; invalid, [u.r0] = 0		
  3156 0000DACA 28CA                <1> 	sub	dl, cl ; end >= start
  3157 0000DACC 726E                <1> 	jc	short sysvideo_6 ; invalid, [u.r0] = 0
  3158                              <1> 	; 21/11/2020
  3159 0000DACE 89D3                <1> 	mov	ebx, edx ; row count - 1
  3160 0000DAD0 7415                <1> 	jz	short sysvideo_4_2
  3161 0000DAD2 50                  <1> 	push	eax ; *****
  3162 0000DAD3 B8A0000000          <1> 	mov	eax, 80*2 ; bytes per row
  3163 0000DAD8 F7E3                <1> 	mul	ebx ; 21/11/2020
  3164                              <1> 		; eax = window end offset 
  3165                              <1> 		; (for the last row, before adding column bytes)
  3166 0000DADA 01C6                <1> 	add	esi, eax
  3167 0000DADC 01C7                <1> 	add	edi, eax
  3168 0000DADE 58                  <1> 	pop	eax ; ***** ; mode 3 video memory end (0C000h)
  3169 0000DADF 39C6                <1> 	cmp	esi, eax
  3170                              <1> 	;ja	short sysvideo_6 ; invalid, [u.r0] = 0
  3171 0000DAE1 7359                <1> 	jnb	short sysvideo_6 ; 21/11/2020
  3172 0000DAE3 39C7                <1> 	cmp	edi, eax
  3173                              <1> 	;ja	short sysvideo_6 ; invalid, [u.r0] = 0
  3174 0000DAE5 7355                <1> 	jnb	short sysvideo_6 ; 21/11/2020
  3175                              <1> sysvideo_4_2:
  3176 0000DAE7 59                  <1> 	pop	ecx ; *
  3177 0000DAE8 5A                  <1> 	pop	edx ; **
  3178 0000DAE9 81E1FFFF0000        <1> 	and	ecx, 0FFFFh
  3179 0000DAEF 81E2FFFF0000        <1> 	and	edx, 0FFFFh
  3180                              <1> 	; 21/11/2020
  3181                              <1> 	;cmp	ecx, 79 ; max. 80 columns
  3182 0000DAF5 6683F94F            <1> 	cmp	cx, 79
  3183 0000DAF9 7743                <1> 	ja	short sysvideo_7 ; invalid, [u.r0] = 0
  3184                              <1> 	;cmp	edx, 79 ; max. 80 columns
  3185 0000DAFB 6683FA4F            <1> 	cmp	dx, 79 
  3186 0000DAFF 773D                <1> 	ja	short sysvideo_7 ; invalid, [u.r0] = 0
  3187 0000DB01 28CA                <1> 	sub	dl, cl
  3188 0000DB03 7639                <1> 	jna	short sysvideo_7 ; invalid, [u.r0] = 0
  3189                              <1> 	; 21/11/2020
  3190 0000DB05 740E                <1> 	jz	short sysvideo_4_3 
  3191                              <1> 	; edx = column count (width) - 1
  3192 0000DB07 D0E2                <1> 	shl	dl, 1 ; * 2 ; byte offset (in end row)
  3193 0000DB09 01D6                <1> 	add	esi, edx
  3194 0000DB0B 01D7                <1> 	add	edi, edx
  3195                              <1> 		; esi = source page window end offset
  3196                              <1> 		; edi = destination page window end offset
  3197 0000DB0D 39C6                <1> 	cmp	esi, eax ; video memory end
  3198                              <1> 	;ja	short sysvideo_7
  3199 0000DB0F 732D                <1> 	jnb	short sysvideo_7 ; 21/11/2020
  3200 0000DB11 39C7                <1> 	cmp	edi, eax ; video memory end
  3201                              <1> 	;ja	short sysvideo_7
  3202 0000DB13 7329                <1> 	jnb	short sysvideo_7 ; 21/11/2020
  3203                              <1> sysvideo_4_3:
  3204 0000DB15 5F                  <1> 	pop	edi ; ***
  3205 0000DB16 5E                  <1> 	pop	esi ; ****
  3206 0000DB17 FEC3                <1> 	inc	bl ; row count - 1 -> row count	
  3207 0000DB19 FEC2                <1> 	inc	dl ; column count
  3208 0000DB1B 88D7                <1> 	mov	bh, dl
  3209 0000DB1D D0E2                <1> 	shl	dl, 1 ; convert column count to byte offset
  3210                              <1> 	; 21/11/2020
  3211                              <1> 	; esi = source page window start offset
  3212                              <1> 	; edi = destination page window start offset
  3213 0000DB1F B8A0000000          <1> 	mov	eax, 80*2 ; bytes per row
  3214                              <1> 	; Note: 160 bytes per row (even if move count < 160)
  3215                              <1> sysvideo_5:	
  3216 0000DB24 88F9                <1> 	mov	cl, bh ; move/transfer -word- count per row
  3217 0000DB26 0115[64030300]      <1> 	add	[u.r0], edx ; transfer count in bytes
  3218 0000DB2C F366A5              <1> 	rep	movsw
  3219 0000DB2F 01C6                <1> 	add	esi, eax ; + 160 bytes to next row
  3220 0000DB31 01C7                <1> 	add	edi, eax ; + 160 bytes to next row
  3221 0000DB33 FECB                <1> 	dec	bl ; remain count of rows
  3222 0000DB35 75ED                <1> 	jnz	short sysvideo_5
  3223 0000DB37 E95EF4FFFF          <1> 	jmp	sysret
  3224                              <1> 
  3225                              <1> sysvideo_6:
  3226 0000DB3C 59                  <1> 	pop	ecx ; *
  3227 0000DB3D 5A                  <1> 	pop	edx ; **
  3228                              <1> sysvideo_7:	
  3229 0000DB3E 5F                  <1> 	pop	edi ; ***
  3230 0000DB3F 5E                  <1> 	pop	esi ; ****
  3231 0000DB40 E955F4FFFF          <1> 	jmp	sysret
  3232                              <1> 
  3233                              <1> sysvideo_9:
  3234                              <1> 	; user to system or system to user window transfer
  3235 0000DB45 80FB02              <1> 	cmp	bl, 2
  3236 0000DB48 0F874CF4FFFF        <1>         ja      sysret	; user to user transfer is invalid
  3237                              <1> 			; [u.r0] = 0
  3238                              <1> 
  3239 0000DB4E 56                  <1> 	push	esi ; ****
  3240 0000DB4F 57                  <1> 	push	edi ; ***
  3241 0000DB50 52                  <1> 	push	edx ; **
  3242 0000DB51 51                  <1> 	push	ecx ; *
  3243                              <1> 
  3244 0000DB52 C1E910              <1> 	shr	ecx, 16 ; top row
  3245 0000DB55 C1EA10              <1> 	shr	edx, 16 ; bottom row
  3246                              <1> 	
  3247                              <1> 	; 21/11/2020
  3248                              <1> 	;cmp	ecx, 24 ; max. 25 rows
  3249 0000DB58 6683F918            <1> 	cmp	cx, 24
  3250 0000DB5C 77DE                <1> 	ja	short sysvideo_6 ; invalid, [u.r0] = 0
  3251                              <1> 	;cmp	edx, 24 ; max. 25 rows
  3252 0000DB5E 6683FA18            <1> 	cmp	dx, 24
  3253 0000DB62 77D8                <1> 	ja	short sysvideo_6 ; invalid, [u.r0] = 0	
  3254 0000DB64 28CA                <1> 	sub	dl, cl
  3255 0000DB66 72D4                <1> 	jc	short sysvideo_6 ; invalid, [u.r0] = 0
  3256                              <1> 
  3257                              <1> 	;mov	ch, cl ; top row
  3258                              <1> 	;mov	cl, [ACTIVE_PAGE]
  3259                              <1> 
  3260                              <1> 	;mov	edi, 80*25*2 ; 4000
  3261                              <1> 	; 21/11/2020
  3262                              <1> 	;mov	edi, 4096 ; [CRT_LEN = 4096 for video mode 3 
  3263                              <1> 	;shl	edi, cl  ; ! wrong for page 2 to page 7 !
  3264                              <1> 	;;add	edi, 0B8000h - 80*25*2
  3265                              <1> 	;add	edi, 0B8000h - 1000h ; - 4096
  3266                              <1> 	
  3267                              <1> 	; 21/11/2020
  3268                              <1> 	;xor	eax, eax
  3269                              <1> 	;mov	edi, 0B8000h
  3270                              <1> 	;and	cl, cl ; is video page = 0 ?
  3271                              <1> 	;jz	short sysvideo_9_1 ; yes
  3272                              <1> 	; eax = 0
  3273                              <1> 
  3274                              <1> ;sysvideo_9_0:
  3275                              <1> 	;add	ax, 4096
  3276                              <1> 	;dec	cl
  3277                              <1> 	;jnz	short sysvideo_9_0
  3278                              <1> 	;add	edi, eax
  3279                              <1> 	;	; edi = video page start address
  3280                              <1> 
  3281                              <1> 	; 21/11/2020
  3282 0000DB68 BF00800B00          <1> 	mov	edi, 0B8000h
  3283 0000DB6D 803D[AE5E0100]00    <1> 	cmp	byte [ACTIVE_PAGE], 0
  3284 0000DB74 760C                <1> 	jna	short sysvideo_9_1
  3285                              <1> stsvideo_9_0:
  3286 0000DB76 B010                <1> 	mov	al, 16 ; 4096/256
  3287 0000DB78 F625[AE5E0100]      <1> 	mul	byte [ACTIVE_PAGE] 
  3288 0000DB7E 86E0                <1> 	xchg	ah, al ; * 256
  3289 0000DB80 01C7                <1> 	add	edi, eax
  3290                              <1> 		; edi = video page start address
  3291                              <1> sysvideo_9_1:
  3292                              <1> 	; bl = transfer direction 
  3293                              <1> 	;     ( 1 = from user, 2 = to user)
  3294 0000DB82 88D7                <1> 	mov	bh, dl ; row count - 1
  3295                              <1> 	;mov	dl, ch ; top row
  3296                              <1> 	; 21/11/2020
  3297 0000DB84 08C9                <1> 	or	cl, cl ; top row number
  3298 0000DB86 7408                <1> 	jz	short sysvideo_9_2
  3299                              <1> 
  3300                              <1> 	;mov	eax, 80*2
  3301 0000DB88 66B8A000            <1> 	mov	ax, 80*2 ; 160, bytes per row
  3302 0000DB8C F7E1                <1> 	mul	ecx ; 22/11/2020
  3303 0000DB8E 01C7                <1> 	add	edi, eax
  3304                              <1> 		; edi = window start address for top row
  3305                              <1> sysvideo_9_2:
  3306 0000DB90 59                  <1> 	pop	ecx ; *
  3307 0000DB91 5A                  <1> 	pop	edx ; **
  3308 0000DB92 81E1FFFF0000        <1> 	and	ecx, 0FFFFh
  3309 0000DB98 81E2FFFF0000        <1> 	and	edx, 0FFFFh
  3310                              <1> 	; 21/11/2020
  3311                              <1> 	;cmp	ecx, 79 ; max. 80 columns
  3312 0000DB9E 6683F94F            <1> 	cmp	cx, 79
  3313 0000DBA2 779A                <1> 	ja	short sysvideo_7 ; invalid, [u.r0] = 0
  3314                              <1> 	;cmp	edx, 79 ; max. 80 columns
  3315 0000DBA4 6683FA4F            <1> 	cmp	dx, 79
  3316 0000DBA8 7794                <1> 	ja	short sysvideo_7 ; invalid, [u.r0] = 0
  3317                              <1> 	
  3318 0000DBAA 28CA                <1> 	sub	dl, cl
  3319 0000DBAC 7290                <1> 	jc	short sysvideo_7 ; invalid, [u.r0] = 0
  3320                              <1> 	
  3321 0000DBAE 08C9                <1> 	or	cl, cl ; left column 
  3322 0000DBB0 7404                <1> 	jz	short sysvideo_9_3 ; 0
  3323                              <1> 
  3324                              <1> 	; 21/11/2020
  3325 0000DBB2 D0E1                <1> 	shl	cl, 1  ; column * 2
  3326 0000DBB4 01CF                <1> 	add	edi, ecx
  3327                              <1> 		; edi = window start addr for top left column
  3328                              <1> sysvideo_9_3:
  3329 0000DBB6 88D1                <1> 	mov	cl, dl
  3330 0000DBB8 FEC1                <1> 	inc	cl ; column count
  3331 0000DBBA D0E1                <1> 	shl	cl, 1 ; column count * 2
  3332                              <1> 		; ecx = tranfer count per row
  3333                              <1> 
  3334 0000DBBC 58                  <1> 	pop	eax ; *** (swap address)
  3335 0000DBBD 5E                  <1> 	pop	esi ; ****
  3336                              <1> 
  3337 0000DBBE FEC7                <1> 	inc	bh  ; row count	
  3338                              <1> 	
  3339                              <1> 	;mov	edx, 80*2
  3340 0000DBC0 B2A0                <1> 	mov	dl, 80*2  ; bytes per row
  3341                              <1> 	;
  3342 0000DBC2 80FB01              <1> 	cmp	bl, 1 ; transfer direction
  3343 0000DBC5 7742                <1> 	ja	short sysvideo_11 ; system to user transfer
  3344                              <1> 
  3345                              <1> 	; user to system video/display page window transfer (mode 0)	
  3346 0000DBC7 21C0                <1> 	and	eax, eax ; swap address
  3347 0000DBC9 7420                <1> 	jz	short sysvideo_10 ; no window swap
  3348                              <1> 	; save previous window content in user's buffer (swap address)
  3349 0000DBCB 56                  <1> 	push	esi ; user buffer
  3350 0000DBCC 57                  <1> 	push	edi ; beginning address of the window
  3351                              <1> 	; 21/11/2020
  3352 0000DBCD 53                  <1> 	push	ebx ; save bh
  3353 0000DBCE 89FE                <1> 	mov	esi, edi
  3354 0000DBD0 89C7                <1> 	mov	edi, eax
  3355                              <1> sysvideo_9_4:
  3356 0000DBD2 E88B110000          <1> 	call	transfer_to_user_buffer ; fast transfer
  3357 0000DBD7 7208                <1> 	jc	short sysvideo_9_5
  3358                              <1> 	; ecx = actual transfer count (must be same with input)
  3359 0000DBD9 01D6                <1> 	add	esi, edx ; next row address of (video page) window 
  3360 0000DBDB 01CF                <1> 	add	edi, ecx ; next row address of user's window
  3361                              <1> 		; Note: ecx may be less than row length of video page
  3362                              <1> 		; user's window uses offset according to window width
  3363 0000DBDD FECF                <1> 	dec	bh
  3364 0000DBDF 75F1                <1> 	jnz	short sysvideo_9_4 ; repeat for next row
  3365                              <1> sysvideo_9_5:
  3366 0000DBE1 5B                  <1> 	pop	ebx ; restore bh
  3367 0000DBE2 5F                  <1> 	pop	edi
  3368 0000DBE3 5E                  <1> 	pop	esi
  3369 0000DBE4 7305                <1> 	jnc	short sysvideo_10
  3370 0000DBE6 E9AFF3FFFF          <1> 	jmp	sysret ; [u.r0] = 0
  3371                              <1> sysvideo_10: 
  3372                              <1> 	; user to system video/display page window transfer (mode 0)	
  3373                              <1> 	; esi =	user buffer
  3374 0000DBEB E8BC110000          <1> 	call	transfer_from_user_buffer ; fast transfer
  3375 0000DBF0 0F82A4F3FFFF        <1> 	jc	sysret
  3376                              <1> 	; ecx = actual transfer count (must be same with input)
  3377 0000DBF6 010D[64030300]      <1> 	add	[u.r0], ecx ; actual transfer count
  3378 0000DBFC 01D7                <1> 	add	edi, edx ; next row address of (ivdeo page) window 
  3379 0000DBFE 01CE                <1> 	add	esi, ecx ; next row address of user's window
  3380                              <1> 		; Note: ecx may be less than row length of video page
  3381                              <1> 		; user's window uses offset according to window width
  3382 0000DC00 FECF                <1> 	dec	bh
  3383 0000DC02 75E7                <1> 	jnz	short sysvideo_10 ; repeat for next row
  3384 0000DC04 E991F3FFFF          <1> 	jmp	sysret
  3385                              <1> 	
  3386                              <1> sysvideo_11:
  3387                              <1> 	; system to user video/display page window transfer (mode 0)
  3388 0000DC09 87FE                <1> 	xchg	edi, esi
  3389                              <1> sysvideo_12:
  3390                              <1> 	; esi = beginning addr of the (screen, video page) window
  3391                              <1> 	; edi =	user's buffer	
  3392 0000DC0B E852110000          <1> 	call	transfer_to_user_buffer ; fast transfer
  3393 0000DC10 0F8284F3FFFF        <1> 	jc	sysret
  3394                              <1> 	; ecx = actual transfer count (must be same with input)
  3395 0000DC16 010D[64030300]      <1> 	add	[u.r0], ecx
  3396 0000DC1C 01D6                <1> 	add	esi, edx ; next row (edx = 160)
  3397 0000DC1E 01CF                <1> 	add	edi, ecx ; next row of the user's window 
  3398                              <1> 			 ; (ecx <= 160)
  3399 0000DC20 FECF                <1> 	dec	bh
  3400 0000DC22 75E7                <1> 	jnz	short sysvideo_12
  3401 0000DC24 E971F3FFFF          <1> 	jmp	sysret
  3402                              <1> 
  3403                              <1> sysvideo_13:
  3404 0000DC29 80FF01              <1> 	cmp	bh, 1
  3405 0000DC2C 0F8781030000        <1>         ja      sysvideo_38 ; 23/11/2020
  3406                              <1> 
  3407                              <1> 	; 23/11/2020 (TRDOS 386 v2.0.3)
  3408                              <1> 	; (major modification, from mode 13h to all VGA modes,
  3409                              <1> 	;  except super VGA modes and liner frame buffer method)
  3410                              <1> 
  3411                              <1> 	; BH = 1 = VGA Graphics mode (0A0000h) data transfers
  3412                              <1> 
  3413                              <1> 	; 23/11/2020
  3414                              <1> 	; screen width will be saved into EBP register
  3415                              <1> 
  3416 0000DC32 88DC                <1> 	mov	ah, bl
  3417                              <1> 	;and	bl, 0Fh	
  3418 0000DC34 C0EC04              <1> 	shr	ah, 4
  3419 0000DC37 BD40010000          <1> 	mov	ebp, 320 ; 320*200, 320*240
  3420 0000DC3C 20E4                <1> 	and	ah, ah
  3421 0000DC3E 7413                <1> 	jz	short sysvideo_13_0
  3422 0000DC40 66D1E5              <1> 	shl	bp, 1 ; 640*200, 640*400, 640*480
  3423 0000DC43 80FC02              <1> 	cmp	ah, 2
  3424 0000DC46 720B                <1> 	jb	short sysvideo_13_0		
  3425 0000DC48 0F874CF3FFFF        <1> 	ja	sysret ; invalid
  3426                              <1> 	; 800*600
  3427 0000DC4E 6681C5A000          <1> 	add	bp, 160 ; 800
  3428                              <1> 
  3429                              <1> sysvideo_13_0:
  3430                              <1> 
  3431                              <1> 	;; 21/11/2020 (TRDOS 386 v2.0.3)
  3432                              <1> 	;; VGA graphics mode transfers are only for video mode 13h
  3433                              <1> 
  3434                              <1> 	; 23/11/2020
  3435                              <1> 	;cmp	byte [CRT_MODE], 13h ; 320x200 graphics, 256 colors
  3436                              <1> 	;jne	sysret ; invalid (nothing to do), [u.r0] = 0 
  3437                              <1> 
  3438                              <1> 	;and	bl, bl
  3439 0000DC53 80E30F              <1> 	and	bl, 0Fh
  3440 0000DC56 755A                <1> 	jnz	short sysvideo_14
  3441                              <1> 
  3442                              <1> 	; BL = 0 = Fill color (color in CL) (32K)
  3443                              <1> 
  3444                              <1> 	; 22/11/2020
  3445                              <1> 	;mov	eax, 65536 ; in fact 320*200 pixel bytes (32000)
  3446                              <1> 	;mov	[u.r0], eax
  3447 0000DC58 C605[66030300]01    <1> 	mov	byte [u.r0+2], 1 ; 65536
  3448 0000DC5F BF00000A00          <1> 	mov	edi, 0A0000h
  3449                              <1> 
  3450 0000DC64 08ED                <1> 	or	ch, ch ; mix ?
  3451 0000DC66 7419                <1> 	jz	short sysvideo_13_2 ; no, overwrite
  3452                              <1> 	
  3453                              <1> 	; Mix current pixel colors with mixing (CL input) color
  3454 0000DC68 89FE                <1> 	mov	esi, edi
  3455 0000DC6A 88CB                <1> 	mov	bl, cl ; mixing color 
  3456 0000DC6C 30E4                <1> 	xor	ah, ah
  3457 0000DC6E B900000100          <1> 	mov	ecx, 65536
  3458                              <1> sysvideo_13_1:
  3459 0000DC73 AC                  <1> 	lodsb
  3460 0000DC74 00D8                <1> 	add	al, bl
  3461 0000DC76 66D1E8              <1> 	shr	ax, 1 ; / 2
  3462 0000DC79 AA                  <1> 	stosb
  3463 0000DC7A E2F7                <1> 	loop	sysvideo_13_1
  3464 0000DC7C E919F3FFFF          <1> 	jmp	sysret	
  3465                              <1> 
  3466                              <1> 	; Overwrite pixel colors
  3467                              <1> sysvideo_13_2:
  3468 0000DC81 88CD                <1> 	mov	ch, cl ; color
  3469 0000DC83 6689C8              <1> 	mov	ax, cx
  3470 0000DC86 C1E010              <1> 	shl	eax, 16
  3471 0000DC89 6689C8              <1> 	mov	ax, cx
  3472 0000DC8C B9C2410000          <1> 	mov	ecx, 16834
  3473 0000DC91 F3AB                <1> 	rep	stosd
  3474 0000DC93 E902F3FFFF          <1> 	jmp	sysret
  3475                              <1> 
  3476                              <1> sysvideo_16:
  3477 0000DC98 80FB02              <1> 	cmp	bl, 2	
  3478 0000DC9B 7737                <1> 	ja	short sysvideo_18
  3479                              <1> 	; 23/11/2020
  3480 0000DC9D 7213                <1> 	jb	short sysvideo_14
  3481                              <1> 
  3482 0000DC9F 89CF                <1> 	mov	edi, ecx ; user's buffer
  3483                              <1> 	; BL = 2 = system to user video/display page transfer
  3484                              <1> sysvideo_17:
  3485                              <1> 	; 22/11/2020
  3486 0000DCA1 BE00000A00          <1> 	mov	esi, 0A0000h
  3487 0000DCA6 B900000100          <1> 	mov	ecx, 65536
  3488 0000DCAB E8B2100000          <1> 	call	transfer_to_user_buffer ; fast transfer
  3489                              <1> 	;jc	sysret ; [u.r0] = 0
  3490                              <1> 	;mov	[u.r0], ecx ; actual transfer count (32768)
  3491                              <1> 	;jmp	sysret
  3492                              <1> 	; 23/11/2020
  3493 0000DCB0 EB11                <1> 	jmp	short sysvideo_15_0 	
  3494                              <1> 
  3495                              <1> sysvideo_14:
  3496                              <1> 	; 23/11/2020
  3497                              <1> 	;cmp	bl, 1
  3498                              <1> 	;ja	short sysvideo_16
  3499                              <1> 
  3500 0000DCB2 89CE                <1> 	mov	esi, ecx ; user's buffer
  3501                              <1> 	; BL = 1 = user to system video/display page transfer
  3502                              <1> sysvideo_15:
  3503                              <1> 	; 22/11/2020
  3504 0000DCB4 BF00000A00          <1> 	mov	edi, 0A0000h
  3505                              <1> 	; edi = video page address
  3506 0000DCB9 B900000100          <1> 	mov	ecx, 65536
  3507 0000DCBE E8E9100000          <1> 	call	transfer_from_user_buffer ; fast transfer
  3508                              <1> sysvideo_15_0:
  3509 0000DCC3 0F82D1F2FFFF        <1> 	jc	sysret ; [u.r0] = 0
  3510 0000DCC9 890D[64030300]      <1> 	mov	[u.r0], ecx ; actual transfer count (32768)		
  3511 0000DCCF E9C6F2FFFF          <1> 	jmp	sysret
  3512                              <1> 
  3513                              <1> sysvideo_18:
  3514 0000DCD4 80FB03              <1> 	cmp	bl, 3
  3515 0000DCD7 0F8780000000        <1> 	ja	sysvideo_23
  3516                              <1> 
  3517                              <1> 	; BL = 3 = NOT bits in window (ECX, EDX)
  3518                              <1> 
  3519                              <1> 	; 22/11/2020
  3520 0000DCDD BF00000A00          <1> 	mov	edi, 0A0000h
  3521 0000DCE2 89FE                <1> 	mov	esi, edi
  3522                              <1> 	
  3523                              <1> 	; 21/11/2020
  3524 0000DCE4 39CA                <1> 	cmp	edx, ecx ; bottom-right > top-left ?
  3525 0000DCE6 731E                <1> 	jnb	short sysvideo_20 ; window
  3526                              <1> 
  3527 0000DCE8 09D2                <1> 	or	edx, edx
  3528 0000DCEA 0F85AAF2FFFF        <1> 	jnz	sysret  ; invalid !
  3529                              <1> 
  3530                              <1> 	; full screen (update) ; edx = 0, ecx > 0
  3531                              <1> 	;mov	ecx, 66536
  3532                              <1> 	; 21/11/2020
  3533 0000DCF0 B900400000          <1> 	mov	ecx, 16384  ; dword 'NOT'
  3534 0000DCF5 66890D[64030300]    <1> 	mov	[u.r0], cx
  3535                              <1> sysvideo_19:
  3536                              <1> 	;not	byte [esi] ; NOT operation
  3537                              <1> 	;inc	esi
  3538 0000DCFC F716                <1> 	not	dword [esi]
  3539 0000DCFE AD                  <1> 	lodsd	; add esi, 4
  3540 0000DCFF E2FB                <1> 	loop	sysvideo_19
  3541 0000DD01 E994F2FFFF          <1> 	jmp	sysret
  3542                              <1> sysvideo_20:
  3543 0000DD06 0FB7C2              <1> 	movzx	eax, dx ; bottom right column
  3544 0000DD09 6629C8              <1> 	sub	ax, cx  ; - top left column
  3545 0000DD0C 0F8288F2FFFF        <1>         jb      sysret ; invalid
  3546 0000DD12 6640                <1> 	inc	ax ; same column no == 1 column	 
  3547 0000DD14 50                  <1> 	push	eax ; byte count per window row
  3548 0000DD15 52                  <1> 	push	edx
  3549                              <1> 	;mov	ebx, 320 ; screen width
  3550                              <1> 	; 23/11/2020
  3551 0000DD16 89EB                <1> 	mov	ebx, ebp ; 320,600,800
  3552 0000DD18 89C8                <1> 	mov	eax, ecx
  3553 0000DD1A C1E810              <1> 	shr	eax, 16  ; top row
  3554 0000DD1D F7E3                <1> 	mul	ebx
  3555 0000DD1F 6689CA              <1> 	mov	dx, cx ; top left column
  3556 0000DD22 01D0                <1> 	add	eax, edx
  3557 0000DD24 01C6                <1> 	add	esi, eax ; start address 
  3558 0000DD26 59                  <1> 	pop	ecx ; edx
  3559 0000DD27 89C8                <1> 	mov	eax, ecx
  3560 0000DD29 C1E810              <1> 	shr	eax, 16 ; bottom row
  3561 0000DD2C F7E3                <1> 	mul	ebx
  3562 0000DD2E 6689CA              <1> 	mov	dx, cx ; bottom right column
  3563 0000DD31 01D0                <1> 	add	eax, edx
  3564 0000DD33 01C7                <1> 	add	edi, eax ; stop address (included)
  3565 0000DD35 5A                  <1> 	pop	edx ; byte count per window row
  3566 0000DD36 81FFFFFF0A00        <1> 	cmp	edi, 0AFFFFh ; 22/11/2020
  3567 0000DD3C 0F8758F2FFFF        <1> 	ja	sysret
  3568                              <1> 	; 21/11/2020
  3569 0000DD42 29D3                <1> 	sub	ebx, edx ; screen width - window width
  3570 0000DD44 4E                  <1> 	dec	esi 
  3571                              <1> sysvideo_21:
  3572                              <1> 	;push	esi
  3573 0000DD45 89D1                <1> 	mov	ecx, edx ; window width (byte count)
  3574                              <1> sysvideo_22:
  3575 0000DD47 46                  <1> 	inc	esi
  3576 0000DD48 F616                <1> 	not	byte [esi]
  3577                              <1> 	;inc	esi
  3578 0000DD4A E2FB                <1> 	loop	sysvideo_22
  3579                              <1> 	; 21/11/2020
  3580 0000DD4C 0115[64030300]      <1> 	add	[u.r0], edx
  3581                              <1> 	;pop	esi ; 21/11/2020
  3582                              <1> 	;add	esi, ebx ; bytes per screen row (320)
  3583 0000DD52 01DE                <1> 	add	esi, ebx ; add difference for next row
  3584                              <1> 	;
  3585 0000DD54 39FE                <1> 	cmp	esi, edi ; stop address (included in loop)
  3586                              <1> 	;jna	short sysvideo_21
  3587 0000DD56 72ED                <1> 	jb	short sysvideo_21
  3588 0000DD58 E93DF2FFFF          <1> 	jmp	sysret
  3589                              <1> 
  3590                              <1> sysvideo_23:
  3591 0000DD5D 80FB04              <1> 	cmp	bl, 4
  3592 0000DD60 0F87A3000000        <1>         ja      sysvideo_26
  3593                              <1> 
  3594                              <1> 	; BL = 4 = window copy (system to system)
  3595                              <1> 
  3596                              <1> 	; 22/11/2020
  3597 0000DD66 B800000A00          <1> 	mov	eax, 0A0000h
  3598 0000DD6B 39C6                <1> 	cmp	esi, eax
  3599 0000DD6D 0F8227F2FFFF        <1> 	jb	sysret
  3600 0000DD73 39C7                <1> 	cmp	edi, eax
  3601 0000DD75 0F821FF2FFFF        <1> 	jb	sysret
  3602                              <1> 	;add	ax, 0FFFFh
  3603 0000DD7B 66B8FFFF            <1> 	mov	ax, 0FFFFh ; 65535
  3604 0000DD7F 39C6                <1> 	cmp	esi, eax
  3605 0000DD81 0F8713F2FFFF        <1> 	ja	sysret
  3606 0000DD87 39C7                <1> 	cmp	edi, eax
  3607 0000DD89 0F870BF2FFFF        <1> 	ja	sysret
  3608                              <1> 	
  3609 0000DD8F 39CA                <1> 	cmp	edx, ecx ; bottom-right > top-left ?
  3610 0000DD91 731A                <1> 	jnb	short sysvideo_24 ; window
  3611                              <1> 
  3612 0000DD93 09D2                <1> 	or	edx, edx
  3613 0000DD95 0F85FFF1FFFF        <1> 	jnz	sysret  ; invalid !
  3614                              <1> 
  3615                              <1> 	; full screen copy ; edx = 0, ecx > 0
  3616 0000DD9B B900000100          <1> 	mov	ecx, 65536
  3617 0000DDA0 890D[64030300]      <1> 	mov	[u.r0], ecx
  3618 0000DDA6 F3A4                <1> 	rep	movsb
  3619 0000DDA8 E9EDF1FFFF          <1> 	jmp	sysret
  3620                              <1> sysvideo_24:
  3621 0000DDAD 0FB7C2              <1> 	movzx	eax, dx ; bottom right column
  3622 0000DDB0 6629C8              <1> 	sub	ax, cx  ; - top left column
  3623 0000DDB3 0F82E1F1FFFF        <1>         jb      sysret ; invalid
  3624 0000DDB9 6640                <1> 	inc	ax ; same column no == 1 column	 
  3625 0000DDBB 50                  <1> 	push	eax ; byte count per window row
  3626                              <1> 	;
  3627 0000DDBC 52                  <1> 	push	edx
  3628                              <1> 	;mov	ebx, 320 ; screen width
  3629                              <1> 	; 23/11/2020
  3630 0000DDBD 89EB                <1> 	mov	ebx, ebp ; 320,600,800
  3631 0000DDBF 89C8                <1> 	mov	eax, ecx
  3632 0000DDC1 C1E810              <1> 	shr	eax, 16	; top row
  3633 0000DDC4 F7E3                <1> 	mul	ebx
  3634 0000DDC6 6689CA              <1> 	mov	dx, cx ; top left column
  3635 0000DDC9 01D0                <1> 	add	eax, edx
  3636 0000DDCB 01C7                <1> 	add	edi, eax ; start address 
  3637 0000DDCD 01C6                <1> 	add	esi, eax
  3638 0000DDCF 59                  <1> 	pop	ecx ; edx
  3639 0000DDD0 89C8                <1> 	mov	eax, ecx
  3640 0000DDD2 C1E810              <1> 	shr	eax, 16 ; bottom row
  3641 0000DDD5 F7E3                <1> 	mul	ebx
  3642 0000DDD7 6689CA              <1> 	mov	dx, cx ; bottom right column
  3643 0000DDDA 01D0                <1> 	add	eax, edx
  3644 0000DDDC 5A                  <1> 	pop	edx ; byte count per window row
  3645 0000DDDD 0500000A00          <1> 	add	eax, 0A0000h
  3646 0000DDE2 3DFFFF0A00          <1> 	cmp	eax, 0AFFFFh
  3647 0000DDE7 0F87ADF1FFFF        <1> 	ja	sysret
  3648 0000DDED 57                  <1> 	push	edi ; start address 
  3649 0000DDEE 50                  <1> 	push	eax ; stop address (included)
  3650                              <1> 	; 21/11/2020
  3651 0000DDEF 29D3                <1> 	sub	ebx, edx ; screen width - window width
  3652                              <1> sysvideo_25:
  3653 0000DDF1 89D1                <1> 	mov	ecx, edx
  3654 0000DDF3 F3A4                <1> 	rep	movsb
  3655                              <1> 	; 21/11/2020
  3656 0000DDF5 0115[64030300]      <1> 	add	[u.r0], edx ; window width (byte count)
  3657                              <1> 	;or	ebx, ebx
  3658                              <1> 	;jz	short sysvideo_25_0
  3659 0000DDFB 01DF                <1> 	add	edi, ebx ; add difference (for next row) 
  3660 0000DDFD 01DE                <1> 	add	esi, ebx
  3661                              <1> ;sysvideo_25_0:
  3662 0000DDFF 3B3C24              <1> 	cmp	edi, [esp] ; stop addr (included in loop)
  3663 0000DE02 76ED                <1> 	jna	short sysvideo_25
  3664                              <1> 	; 21/11/2020
  3665 0000DE04 E98B000000          <1> 	jmp	sysvideo_28
  3666                              <1> 	;pop	ebx ; stop address
  3667                              <1> 	;pop	edi ; start address
  3668                              <1> 	;jmp	sysret
  3669                              <1> 
  3670                              <1> sysvideo_26:
  3671 0000DE09 80FB05              <1> 	cmp	bl, 5
  3672 0000DE0C 0F8789000000        <1>         ja      sysvideo_29
  3673                              <1> 
  3674                              <1> 	; BL = 5 = window copy (user to system)
  3675                              <1> 
  3676                              <1> 	; 22/11/2020
  3677 0000DE12 B800000A00          <1> 	mov	eax, 0A0000h
  3678 0000DE17 39C7                <1> 	cmp	edi, eax
  3679 0000DE19 0F827BF1FFFF        <1> 	jb	sysret
  3680                              <1> 	;add	ax, 0FFFFh ; 65535
  3681 0000DE1F 66B8FFFF            <1> 	mov	ax, 0FFFFh
  3682 0000DE23 39C7                <1> 	cmp	edi, eax
  3683 0000DE25 0F876FF1FFFF        <1> 	ja	sysret
  3684                              <1> 
  3685                              <1> 	; 21/11/2020
  3686                              <1> 	; esi = user buffer (in user's memory space)
  3687 0000DE2B 39CA                <1> 	cmp	edx, ecx ; bottom-right > top-left ?
  3688 0000DE2D 730D                <1>       	jnb	short sysvideo_26_0 ; window
  3689                              <1> 
  3690 0000DE2F 09D2                <1> 	or	edx, edx
  3691 0000DE31 0F8563F1FFFF        <1> 	jnz	sysret  ; invalid !
  3692                              <1> 
  3693                              <1> 	; full screen copy ; edx = 0, ecx > 0
  3694 0000DE37 E978FEFFFF          <1> 	jmp	sysvideo_15 ; full screen copy
  3695                              <1> 
  3696                              <1> sysvideo_26_0:
  3697 0000DE3C 0FB7C2              <1> 	movzx	eax, dx ; bottom right column
  3698 0000DE3F 6629C8              <1> 	sub	ax, cx  ; - top left column
  3699 0000DE42 0F8252F1FFFF        <1>         jb      sysret ; invalid
  3700 0000DE48 6640                <1> 	inc	ax ; same column no == 1 column	 
  3701 0000DE4A 50                  <1> 	push	eax ; byte count per window row
  3702                              <1> 
  3703 0000DE4B 52                  <1> 	push	edx
  3704                              <1> 	;mov	ebx, 320 ; screen width
  3705                              <1> 	; 23/11/2020
  3706 0000DE4C 89EB                <1> 	mov	ebx, ebp ; 320,600,800
  3707 0000DE4E 89C8                <1> 	mov	eax, ecx
  3708 0000DE50 C1E810              <1> 	shr	eax, 16	; top row
  3709 0000DE53 F7E3                <1> 	mul	ebx
  3710 0000DE55 6689CA              <1> 	mov	dx, cx ; top left column
  3711 0000DE58 01D0                <1> 	add	eax, edx
  3712 0000DE5A 01C7                <1> 	add	edi, eax ; start address 
  3713 0000DE5C 59                  <1> 	pop	ecx ; edx
  3714 0000DE5D 89C8                <1> 	mov	eax, ecx
  3715 0000DE5F C1E810              <1> 	shr	eax, 16 ; bottom row
  3716 0000DE62 F7E3                <1> 	mul	ebx
  3717 0000DE64 6689CA              <1> 	mov	dx, cx ; bottom right column
  3718 0000DE67 01D0                <1> 	add	eax, edx
  3719 0000DE69 5A                  <1> 	pop	edx ; byte count per window row
  3720 0000DE6A 0500000A00          <1> 	add	eax, 0A0000h
  3721 0000DE6F 3DFFFF0A00          <1> 	cmp	eax, 0AFFFFh
  3722 0000DE74 0F8720F1FFFF        <1> 	ja	sysret
  3723                              <1> 
  3724 0000DE7A 57                  <1> 	push	edi ; start address 
  3725 0000DE7B 50                  <1> 	push	eax ; stop address (included)
  3726                              <1> sysvideo_27:
  3727 0000DE7C 89D1                <1> 	mov	ecx, edx ; byte count
  3728                              <1> 	; user to system video/display page window transfer
  3729                              <1> 	; esi =	user buffer
  3730 0000DE7E E8290F0000          <1> 	call	transfer_from_user_buffer ; fast transfer
  3731 0000DE83 720F                <1> 	jc	short sysvideo_28
  3732                              <1> 		; ecx = actual transfer count (= ecx input) 
  3733 0000DE85 010D[64030300]      <1> 	add	[u.r0], ecx
  3734 0000DE8B 01DF                <1> 	add	edi, ebx ; next row in video memory window
  3735 0000DE8D 01CE                <1> 	add	esi, ecx ; next window row in user's buffer
  3736 0000DE8F 3B3C24              <1> 	cmp	edi, [esp] ; stop addr (included in loop)
  3737 0000DE92 76E8                <1> 	jna	short sysvideo_27
  3738                              <1> sysvideo_28:
  3739 0000DE94 5B                  <1> 	pop	ebx ; stop address
  3740 0000DE95 5F                  <1> 	pop	edi ; start address
  3741                              <1> 	; 21/11/2020
  3742 0000DE96 E9FFF0FFFF          <1> 	jmp	sysret
  3743                              <1> 
  3744                              <1> sysvideo_29:
  3745 0000DE9B 80FB06              <1> 	cmp	bl, 6
  3746                              <1> 	;ja	sysvideo_32
  3747                              <1> 	; 21/11/2020
  3748 0000DE9E 0F878D000000        <1> 	ja	sysvideo_31
  3749                              <1> 
  3750                              <1> 	; BL = 6 = window copy (system to user)
  3751                              <1> 
  3752 0000DEA4 89F7                <1> 	mov	edi, esi ; user buffer
  3753                              <1> 
  3754                              <1> 	; 22/11/2020
  3755 0000DEA6 B800000A00          <1> 	mov	eax, 0A0000h
  3756 0000DEAB 39C6                <1> 	cmp	esi, eax
  3757 0000DEAD 0F82E7F0FFFF        <1> 	jb	sysret
  3758                              <1> 	;add	ax, 0FFFFh ; 65535
  3759 0000DEB3 66B8FFFF            <1> 	mov	ax, 0FFFFh
  3760 0000DEB7 39C6                <1> 	cmp	esi, eax
  3761 0000DEB9 0F87DBF0FFFF        <1> 	ja	sysret
  3762                              <1> 
  3763                              <1> 	; 21/11/2020
  3764                              <1> 	; edi = user buffer (in user's memory space)
  3765 0000DEBF 39CA                <1> 	cmp	edx, ecx ; bottom-right > top-left ?
  3766 0000DEC1 730D                <1>         jnb     short sysvideo_29_0
  3767                              <1> 	
  3768 0000DEC3 21D2                <1> 	and	edx, edx
  3769 0000DEC5 0F85CFF0FFFF        <1> 	jnz	sysret	; invalid !
  3770                              <1> 
  3771                              <1> 	; full screen copy  ; edx = 0, ecx > 0
  3772 0000DECB E9D1FDFFFF          <1> 	jmp	sysvideo_17
  3773                              <1> 
  3774                              <1> sysvideo_29_0:
  3775 0000DED0 0FB7C2              <1> 	movzx	eax, dx ; bottom right column
  3776 0000DED3 6629C8              <1> 	sub	ax, cx  ; - top left column
  3777 0000DED6 0F82BEF0FFFF        <1>         jb      sysret ; invalid
  3778 0000DEDC 6640                <1> 	inc	ax ; same column no == 1 column	 
  3779 0000DEDE 50                  <1> 	push	eax ; byte count per window row
  3780                              <1> 
  3781 0000DEDF 52                  <1> 	push	edx
  3782                              <1> 	;mov	ebx, 320 ; screen width
  3783                              <1> 	; 23/11/2020
  3784 0000DEE0 89EB                <1> 	mov	ebx, ebp ; 320,600,800
  3785 0000DEE2 89C8                <1> 	mov	eax, ecx
  3786 0000DEE4 C1E810              <1> 	shr	eax, 16	; top row
  3787 0000DEE7 F7E3                <1> 	mul	ebx
  3788 0000DEE9 6689CA              <1> 	mov	dx, cx ; top left column
  3789 0000DEEC 01D0                <1> 	add	eax, edx
  3790 0000DEEE 01C6                <1> 	add	esi, eax ; start address 
  3791 0000DEF0 59                  <1> 	pop	ecx ; edx
  3792 0000DEF1 89C8                <1> 	mov	eax, ecx
  3793 0000DEF3 C1E810              <1> 	shr	eax, 16 ; bottom row
  3794 0000DEF6 F7E3                <1> 	mul	ebx
  3795 0000DEF8 6689CA              <1> 	mov	dx, cx ; bottom right column
  3796 0000DEFB 01D0                <1> 	add	eax, edx
  3797 0000DEFD 5A                  <1> 	pop	edx ; byte count per window row
  3798 0000DEFE 0500000A00          <1> 	add	eax, 0A0000h
  3799 0000DF03 3DFFFF0A00          <1> 	cmp	eax, 0AFFFFh
  3800 0000DF08 0F878CF0FFFF        <1> 	ja	sysret
  3801 0000DF0E 56                  <1> 	push	esi ; start address 
  3802 0000DF0F 50                  <1> 	push	eax ; stop address (included)
  3803                              <1> sysvideo_30:
  3804 0000DF10 89D1                <1> 	mov	ecx, edx ; byte count
  3805                              <1> 	; user to system video/display page window transfer
  3806                              <1> 	; esi =	user buffer
  3807 0000DF12 E84B0E0000          <1> 	call	transfer_to_user_buffer ; fast transfer
  3808                              <1> 	;jc	short sysvideo_31
  3809 0000DF17 0F8277FFFFFF        <1> 	jc	sysvideo_28  ; 21/11/2020
  3810 0000DF1D 010D[64030300]      <1> 	add	[u.r0], ecx
  3811 0000DF23 01DF                <1> 	add	edi, ebx ; next row
  3812 0000DF25 01CE                <1> 	add	esi, ecx
  3813 0000DF27 3B3C24              <1> 	cmp	edi, [esp] ; stop addr(included in loop)
  3814 0000DF2A 76E4                <1> 	jna	short sysvideo_30
  3815                              <1> 	; 21//11/2020
  3816 0000DF2C E963FFFFFF          <1> 	jmp	sysvideo_28
  3817                              <1> ;sysvideo_31:
  3818                              <1> 	;pop	ebx ; stop address
  3819                              <1> 	;pop	edi ; start address
  3820                              <1> 	;jmp	sysret
  3821                              <1> 
  3822                              <1> sysvideo_31:
  3823                              <1> 	; 21/11/2020 (TRDOS 386 v2.0.3)
  3824                              <1> 	; bl = 7, 8, 9, 10, 11, 12
  3825                              <1> 	; (bl > 12 is invalid for current kernel version)
  3826                              <1> 
  3827                              <1> 	; 23/11/2020
  3828 0000DF31 80FB0D              <1> 	cmp	bl, 13
  3829 0000DF34 0F8760F0FFFF        <1> 	ja	sysret
  3830                              <1> 
  3831                              <1> 	; 22/11/2020
  3832 0000DF3A BE00000A00          <1> 	mov	esi, 0A0000h
  3833 0000DF3F 88C8                <1> 	mov	al, cl ; byte for and/or/xor 
  3834 0000DF41 B900000100          <1> 	mov	ecx, 65536 ; byte count
  3835 0000DF46 890D[64030300]      <1> 	mov	[u.r0], ecx ; return with
  3836                              <1> 			   ; byte count of display page
  3837                              <1> 			   ; (eax > 0 -> OK)	
  3838 0000DF4C 80FB0A              <1> 	cmp	bl, 10
  3839 0000DF4F 722D                <1> 	jb	short sysvideo_32  ; 7, 8, 9
  3840 0000DF51 7416                <1> 	je	short sysvideo_31_inc ; 10
  3841 0000DF53 80FB0C              <1> 	cmp	bl, 12
  3842 0000DF56 7218                <1> 	jb	short sysvideo_31_dec ; 11
  3843 0000DF58 741D                <1> 	je	short sysvideo_31_neg ; 12
  3844                              <1> 	; bl = 13
  3845 0000DF5A B900400000          <1> 	mov	ecx, 16384
  3846                              <1> sysvideo_31_not:
  3847                              <1> 	;not	byte [esi]
  3848                              <1> 	;inc	esi
  3849 0000DF5F F716                <1> 	not	dword [esi]
  3850 0000DF61 AD                  <1> 	lodsd
  3851 0000DF62 E2FB                <1> 	loop	sysvideo_31_not
  3852                              <1> sysvideo_31_ok:
  3853 0000DF64 E931F0FFFF          <1> 	jmp	sysret
  3854                              <1> sysvideo_31_inc:
  3855 0000DF69 FE06                <1> 	inc	byte [esi]
  3856 0000DF6B 46                  <1> 	inc	esi
  3857 0000DF6C E2FB                <1> 	loop	sysvideo_31_inc
  3858 0000DF6E EBF4                <1> 	jmp	short sysvideo_31_ok
  3859                              <1> sysvideo_31_dec:
  3860 0000DF70 FE0E                <1> 	dec	byte [esi]
  3861 0000DF72 46                  <1> 	inc	esi
  3862 0000DF73 E2FB                <1> 	loop	sysvideo_31_dec
  3863 0000DF75 EBED                <1> 	jmp	short sysvideo_31_ok
  3864                              <1> sysvideo_31_neg:
  3865 0000DF77 F61E                <1> 	neg	byte [esi]
  3866 0000DF79 46                  <1> 	inc	esi
  3867 0000DF7A E2FB                <1> 	loop	sysvideo_31_neg
  3868 0000DF7C EBE6                <1> 	jmp	short sysvideo_31_ok
  3869                              <1> 
  3870                              <1> sysvideo_32:
  3871                              <1> 	; 22/11/2020
  3872                              <1> 	; bl = 7, 8, 9
  3873                              <1> 	; ecx = 65536 ; byte count
  3874 0000DF7E B900400000          <1> 	mov	ecx, 16384 ; dword count
  3875 0000DF83 88C4                <1> 	mov	ah, al
  3876 0000DF85 6689C2              <1> 	mov	dx, ax
  3877 0000DF88 C1E210              <1> 	shl	edx, 16 
  3878 0000DF8B 6689C2              <1> 	mov	dx, ax
  3879                              <1> 
  3880                              <1> 	;cmp	bl, 7
  3881                              <1> 	;ja	short sysvideo_34
  3882                              <1> 
  3883                              <1> 	; 21/11/2020
  3884 0000DF8E 80FB08              <1> 	cmp	bl, 8
  3885 0000DF91 740C                <1> 	je	short sysvideo_34
  3886 0000DF93 7714                <1> 	ja	short sysvideo_36
  3887                              <1> 
  3888                              <1> 	; BL = 7 = AND display page bytes with CL
  3889                              <1> 
  3890                              <1> 	;mov	esi, 0A0000h
  3891                              <1> 	;mov	al, cl ; 21/11/2020
  3892                              <1> 	;mov	ecx, 65536
  3893                              <1> sysvideo_33:
  3894                              <1> 	;and	[esi], al
  3895                              <1> 	;inc	esi
  3896 0000DF95 21D6                <1> 	and	esi, edx
  3897 0000DF97 AD                  <1> 	lodsd
  3898 0000DF98 E2FB                <1> 	loop	sysvideo_33
  3899 0000DF9A E9FBEFFFFF          <1> 	jmp	sysret 
  3900                              <1> 
  3901                              <1> sysvideo_34:
  3902                              <1> 	; 21/11/2020
  3903                              <1> 	;cmp	bl, 8
  3904                              <1> 	;ja	short sysvideo_36
  3905                              <1> 
  3906                              <1> 	; BL = 8 = OR display page bytes with CL
  3907                              <1> 
  3908                              <1> 	;mov	esi, 0A0000h
  3909                              <1> 	;mov	al, cl ; 21/11/2020
  3910                              <1> 	;mov	ecx, 65536
  3911                              <1> sysvideo_35:
  3912                              <1> 	;or	[esi], al
  3913                              <1> 	;inc	esi
  3914 0000DF9F 09D6                <1> 	or	esi, edx
  3915 0000DFA1 AD                  <1> 	lodsd
  3916 0000DFA2 E2FB                <1> 	loop	sysvideo_35
  3917 0000DFA4 E9F1EFFFFF          <1> 	jmp	sysret	
  3918                              <1> 
  3919                              <1> sysvideo_36:
  3920                              <1> 	; 21/11/2020
  3921                              <1> 	;cmp	bl, 9
  3922                              <1>         ;ja	sysret ; nothing to do
  3923                              <1> 
  3924                              <1> 	; BL = 9 = XOR display page bytes with CL
  3925                              <1> 
  3926                              <1> 	;mov	esi, 0A0000h
  3927                              <1> 	;mov	al, cl ; 21/11/2020
  3928                              <1> 	;mov	ecx, 65536
  3929                              <1> sysvideo_37:
  3930                              <1> 	;xor	[esi], al
  3931                              <1> 	;inc	esi
  3932 0000DFA9 31D6                <1> 	xor	esi, edx
  3933 0000DFAB AD                  <1> 	lodsd
  3934 0000DFAC E2FB                <1> 	loop	sysvideo_37
  3935 0000DFAE E9E7EFFFFF          <1> 	jmp	sysret
  3936                              <1> 
  3937                              <1> sysvideo_38:
  3938 0000DFB3 80FF02              <1> 	cmp	bh, 2
  3939 0000DFB6 7705                <1>         ja      short sysvideo_40
  3940                              <1> 
  3941                              <1> sysvideo_39:
  3942                              <1> 	; 23/11/2020
  3943                              <1> 	; BH = 2
  3944                              <1> 	; Super VGA, LINEAR FRAME BUFFER data transfers
  3945                              <1> 	; Not implemented for yet ! (11/07/2016)
  3946 0000DFB8 E9DDEFFFFF          <1> 	jmp	sysret
  3947                              <1> 
  3948                              <1> ;sysvideo_39:
  3949                              <1> 	; 23/11/2020
  3950                              <1> 	; BH = 3
  3951                              <1> 	; PIXEL READ/WRITE
  3952                              <1> 	; Not implemented for yet ! (23/11/2020)
  3953                              <1> ;	jmp	sysret
  3954                              <1> 
  3955                              <1> sysvideo_40:
  3956                              <1> 	; 23/11/2020
  3957 0000DFBD 80FF04              <1> 	cmp	bh, 4
  3958 0000DFC0 72F6                <1> 	jb	short sysvideo_39 ; bh = 3, pixel r/w
  3959 0000DFC2 7721                <1> 	ja	short sysvideo_41
  3960                              <1> 	
  3961                              <1> 	; BH = 4
  3962                              <1> 	; Direct User Access for CGA video memory.
  3963                              <1> 	; Setup user's page tables for direct access to 0B8000h.
  3964                              <1> 	;
  3965                              <1> 	; Permission checks are not implemented yet !
  3966                              <1> 	; (11/07/2016)
  3967                              <1> 
  3968 0000DFC4 B800800B00          <1> 	mov	eax, 0B8000h
  3969 0000DFC9 B908000000          <1> 	mov	ecx, 8 ; 8 pages (8*4K=32K)
  3970 0000DFCE 89C3                <1> 	mov	ebx, eax ; 12/05/2017 ; virtual = physical
  3971 0000DFD0 E8377EFFFF          <1> 	call	direct_memory_access	
  3972 0000DFD5 0F82BFEFFFFF        <1> 	jc	sysret
  3973                              <1> 	; eax = 0B8000h if there is not an error
  3974 0000DFDB A3[64030300]        <1> 	mov	[u.r0], eax
  3975 0000DFE0 E9B5EFFFFF          <1> 	jmp	sysret
  3976                              <1> 
  3977                              <1> sysvideo_41:
  3978                              <1> 	; 23/11/2020
  3979 0000DFE5 80FF06              <1> 	cmp	bh, 6
  3980                              <1> 	;ja	short sysvideo_44
  3981 0000DFE8 7205                <1> 	jb	short sysvideo_42
  3982                              <1> 
  3983                              <1> 	; BH = 6
  3984                              <1> 	; Direct User Access for (Super VGA) Linear Frame Buffer.
  3985                              <1> 	; Setup user's page tables for direct access to LFB.
  3986                              <1> 	;
  3987                              <1> 	; Not implemented yet !
  3988                              <1> 	; (11/07/2016)
  3989 0000DFEA E9ABEFFFFF          <1> 	jmp	sysret
  3990                              <1> 
  3991                              <1> sysvideo_42:
  3992                              <1> 	; BH = 5
  3993                              <1> 	; Direct User Access for VGA video memory.
  3994                              <1> 	; Setup user's page tables for direct access to 0A0000h.
  3995                              <1> 	;
  3996                              <1> 	; Permission checks are not implemented yet !
  3997                              <1> 	; (11/07/2016)
  3998                              <1> 
  3999 0000DFEF B800000A00          <1> 	mov	eax, 0A0000h
  4000 0000DFF4 B910000000          <1> 	mov	ecx, 16 ; 16 pages (16*4K=64K)
  4001 0000DFF9 89C3                <1> 	mov	ebx, eax ; 12/05/2017 ; virtual = physical
  4002 0000DFFB E80C7EFFFF          <1> 	call	direct_memory_access	
  4003 0000E000 0F8294EFFFFF        <1> 	jc	sysret
  4004                              <1> 	; eax = 0A0000h if there is not an error
  4005 0000E006 A3[64030300]        <1> 	mov	[u.r0], eax
  4006 0000E00B E98AEFFFFF          <1> 	jmp	sysret
  4007                              <1> 
  4008                              <1> ;sysvideo_43:
  4009                              <1> 	; 23/11/2020
  4010                              <1> 	; BH = 7
  4011                              <1> 	; Get (Super/Extended VGA) mode
  4012                              <1> 	; and Linear Frame Buffer info.
  4013                              <1> 	;
  4014                              <1> 	; Not implemented yet !
  4015                              <1> 	; (11/07/2016)
  4016                              <1> ;	jmp	sysret
  4017                              <1> 
  4018                              <1> ;sysvideo_44:
  4019                              <1> 	; 23/11/2020
  4020                              <1> ;	cmp	bh, 8
  4021                              <1> ;	jb	short sysvideo_43 ; video mode & lfb info
  4022                              <1> ;	ja	sysret ; invalid !
  4023                              <1> 
  4024                              <1> 	; BH = 8
  4025                              <1> 	; Set (Super/Extended VGA) mode and color indexes
  4026                              <1> 	;
  4027                              <1> 	; Not implemented yet !
  4028                              <1> 	; (23/11/2020)
  4029                              <1> ;	jmp	sysret
  4030                              <1> 
  4031                              <1> mkdir:
  4032                              <1> 	; 04/12/2015 (14 byte directory names)
  4033                              <1> 	; 12/10/2015
  4034                              <1> 	; 17/06/2015 (Retro UNIX 386 v1 - Beginning)
  4035                              <1> 	; 29/04/2013 - 01/08/2013 (Retro UNIX 8086 v1)
  4036                              <1> 	;
  4037                              <1> 	; 'mkdir' makes a directory entry from the name pointed to
  4038                              <1> 	; by u.namep into the current directory.
  4039                              <1> 	;
  4040                              <1> 	; INPUTS ->
  4041                              <1> 	;    u.namep - points to a file name 
  4042                              <1> 	;	           that is about to be a directory entry.
  4043                              <1> 	;    ii - current directory's i-number.	
  4044                              <1> 	; OUTPUTS ->
  4045                              <1> 	;    u.dirbuf+2 - u.dirbuf+10 - contains file name. 
  4046                              <1> 	;    u.off - points to entry to be filled 
  4047                              <1> 	;	     in the current directory		
  4048                              <1> 	;    u.base - points to start of u.dirbuf.
  4049                              <1> 	;    r1 - contains i-number of current directory 
  4050                              <1> 	;	
  4051                              <1> 	; ((AX = R1)) output
  4052                              <1> 	;
  4053                              <1> 	;    (Retro UNIX Prototype : 11/11/2012, UNIXCOPY.ASM)
  4054                              <1>         ;    ((Modified registers: eAX, eDX, eBX, eCX, eSI, eDI, eBP))  
  4055                              <1> 	;
  4056                              <1> 
  4057                              <1> 	; 17/06/2015 - 32 bit modifications (Retro UNIX 386 v1)
  4058 0000E010 31C0                <1> 	xor 	eax, eax
  4059 0000E012 BF[9A030300]        <1> 	mov     edi, u.dirbuf+2
  4060 0000E017 89FE                <1> 	mov	esi, edi
  4061 0000E019 AB                  <1> 	stosd
  4062 0000E01A AB                  <1> 	stosd
  4063                              <1> 	; 04/12/2015 (14 byte directory names)
  4064 0000E01B AB                  <1> 	stosd
  4065 0000E01C 66AB                <1> 	stosw
  4066                              <1> 		; jsr r0,copyz; u.dirbuf+2; u.dirbuf+10. / clear this
  4067 0000E01E 89F7                <1> 	mov	edi, esi ; offset to u.dirbuf
  4068                              <1> 	; 12/10/2015 ([u.namep] -> ebp)
  4069                              <1> 	;mov 	ebp, [u.namep]
  4070 0000E020 E80D030000          <1> 	call	trans_addr_nmbp ; convert virtual address to physical
  4071                              <1> 		; esi = physical address (page start + offset)
  4072                              <1> 		; ecx = byte count in the page (1 - 4096)
  4073                              <1> 	; edi = offset to u.dirbuf (edi is not modified in trans_addr_nm)
  4074                              <1> 		; mov u.namep,r2 / r2 points to name of directory entry
  4075                              <1> 		; mov $u.dirbuf+2,r3 / r3 points to u.dirbuf+2
  4076                              <1> mkdir_1: ; 1: 
  4077 0000E025 45                  <1> 	inc	ebp ; 12/10/2015
  4078                              <1> 	;
  4079                              <1> 	; / put characters in the directory name in u.dirbuf+2 - u.dirbuf+10
  4080                              <1> 	 ; 01/08/2013
  4081 0000E026 AC                  <1> 	lodsb
  4082                              <1> 		; movb (r2)+,r1 / move character in name to r1
  4083 0000E027 20C0                <1> 	and 	al, al
  4084 0000E029 7427                <1> 	jz 	short mkdir_3 	  
  4085                              <1> 		; beq 1f / if null, done
  4086 0000E02B 3C2F                <1> 	cmp	al, '/'
  4087                              <1> 		; cmp r1,$'/ / is it a "/"?
  4088 0000E02D 7414                <1> 	je	short mkdir_err
  4089                              <1> 	;je	error
  4090                              <1> 		; beq error9 / yes, error
  4091                              <1> 	; 12/10/2015
  4092 0000E02F 6649                <1> 	dec	cx
  4093 0000E031 7505                <1> 	jnz	short mkdir_2
  4094                              <1> 	; 12/10/2015 ([u.namep] -> ebp)
  4095 0000E033 E800030000          <1> 	call	trans_addr_nm ; convert virtual address to physical
  4096                              <1> 		; esi = physical address (page start + offset)
  4097                              <1> 		; ecx = byte count in the page
  4098                              <1> 	; edi = offset to u.dirbuf (edi is not modified in trans_addr_nm)
  4099                              <1> mkdir_2:
  4100 0000E038 81FF[A8030300]      <1> 	cmp     edi, u.dirbuf+16 ; ; 04/12/2015 (10 -> 16) 
  4101                              <1> 		; cmp r3,$u.dirbuf+10. / have we reached the last slot for
  4102                              <1> 				     ; / a char?
  4103 0000E03E 74E5                <1> 	je	short mkdir_1
  4104                              <1> 		; beq 1b / yes, go back
  4105 0000E040 AA                  <1> 	stosb
  4106                              <1> 		; movb r1,(r3)+ / no, put the char in the u.dirbuf
  4107 0000E041 EBE2                <1> 	jmp 	short mkdir_1
  4108                              <1> 		; br 1b / get next char
  4109                              <1> mkdir_err:
  4110                              <1> 	; 17/06/2015
  4111 0000E043 C705[C8030300]1300- <1> 	mov	dword [u.error], ERR_NOT_DIR ; 'not a valid directory !'
  4111 0000E04B 0000                <1>
  4112 0000E04D E928EFFFFF          <1> 	jmp	error
  4113                              <1> 
  4114                              <1> mkdir_3: ; 1:
  4115 0000E052 A1[78030300]        <1> 	mov	eax, [u.dirp]
  4116 0000E057 A3[80030300]        <1> 	mov	[u.off], eax
  4117                              <1> 		; mov u.dirp,u.off / pointer to empty current directory
  4118                              <1> 				 ; / slot to u.off
  4119                              <1> wdir: ; 29/04/2013
  4120 0000E05C C705[84030300]-     <1>         mov     dword [u.base], u.dirbuf
  4120 0000E062 [98030300]          <1>
  4121                              <1> 		; mov $u.dirbuf,u.base / u.base points to created file name
  4122 0000E066 C705[88030300]1000- <1>         mov     dword [u.count], 16 ; 04/12/2015 (10 -> 16) 
  4122 0000E06E 0000                <1>
  4123                              <1> 		; mov $10.,u.count / u.count = 10
  4124 0000E070 66A1[51040300]      <1> 	mov	ax, [ii] 
  4125                              <1> 		; mov ii,r1 / r1 has i-number of current directory
  4126 0000E076 B201                <1> 	mov	dl, 1 ; owner flag mask ; RETRO UNIX 8086 v1 modification !
  4127 0000E078 E8331D0000          <1> 	call 	access
  4128                              <1> 		; jsr r0,access; 1 / get i-node and set its file up 
  4129                              <1> 				 ; / for writing
  4130                              <1> 	; AX = i-number of current directory
  4131                              <1> 	; 01/08/2013
  4132 0000E07D FE05[C6030300]      <1> 	inc     byte [u.kcall] ; the caller is 'mkdir' sign	
  4133 0000E083 E83C0F0000          <1> 	call	writei
  4134                              <1> 		; jsr r0,writei / write into directory
  4135 0000E088 C3                  <1> 	retn	
  4136                              <1> 		; rts r0
  4137                              <1> 
  4138                              <1> sysexec:
  4139                              <1> 	; 18/11/2017
  4140                              <1> 	; 14/11/2017
  4141                              <1> 	; 13/11/2017
  4142                              <1> 	; 24/10/2016, 04/01/2017
  4143                              <1> 	; 24/04/2016 - TRDOS 386 (TRDOS v2.0)
  4144                              <1> 	; 23/06/2015 - 23/10/2015 (Retro UNIX 386 v1)
  4145                              <1> 	; 03/06/2013 - 06/12/2013 (Retro UNIX 8086 v1)
  4146                              <1> 	;
  4147                              <1> 	; 'sysexec' initiates execution of a file whose path name if
  4148                              <1> 	; pointed to by 'name' in the sysexec call. 
  4149                              <1> 	; 'sysexec' performs the following operations:
  4150                              <1> 	;    1. obtains i-number of file to be executed via 'namei'.
  4151                              <1> 	;    2. obtains i-node of file to be exceuted via 'iget'.
  4152                              <1> 	;    3. sets trap vectors to system routines.
  4153                              <1> 	;    4. loads arguments to be passed to executing file into
  4154                              <1> 	;	highest locations of user's core
  4155                              <1> 	;    5. puts pointers to arguments in locations immediately
  4156                              <1> 	;	following arguments.
  4157                              <1> 	;    6.	saves number of arguments in next location.
  4158                              <1> 	;    7. intializes user's stack area so that all registers
  4159                              <1> 	;	will be zeroed and the PS is cleared and the PC set
  4160                              <1> 	;	to core when 'sysret' restores registers 
  4161                              <1> 	;	and does an rti.
  4162                              <1> 	;    8. inializes u.r0 and u.sp
  4163                              <1> 	;    9. zeros user's core down to u.r0
  4164                              <1> 	;   10.	reads executable file from storage device into core
  4165                              <1> 	;	starting at location 'core'.
  4166                              <1> 	;   11.	sets u.break to point to end of user's code with
  4167                              <1> 	;	data area appended.
  4168                              <1> 	;   12.	calls 'sysret' which returns control at location
  4169                              <1> 	;	'core' via 'rti' instruction. 		  		
  4170                              <1> 	;
  4171                              <1> 	; Calling sequence:
  4172                              <1> 	;	sysexec; namep; argp
  4173                              <1> 	; Arguments:
  4174                              <1> 	;	namep - points to pathname of file to be executed
  4175                              <1> 	;	argp  - address of table of argument pointers
  4176                              <1> 	;	argp1... argpn - table of argument pointers
  4177                              <1> 	;	argp1:<...0> ... argpn:<...0> - argument strings
  4178                              <1> 	; Inputs: (arguments)
  4179                              <1> 	; Outputs: -	
  4180                              <1> 	; ...............................................................
  4181                              <1> 	;
  4182                              <1> 	; Retro UNIX 386 v1 modification: 
  4183                              <1> 	;	User application runs in it's own virtual space 
  4184                              <1> 	;	which is izolated from kernel memory (and other
  4185                              <1> 	;	memory pages) via 80386	paging in ring 3 
  4186                              <1> 	;	privilige mode. Virtual start address is always 0.
  4187                              <1> 	;	User's core memory starts at linear address 400000h
  4188                              <1> 	;	(the end of the 1st 4MB).
  4189                              <1> 	;
  4190                              <1> 	; Retro UNIX 8086 v1 modification: 
  4191                              <1> 	;	user/application segment and system/kernel segment
  4192                              <1> 	;	are different and sysenter/sysret/sysrele routines
  4193                              <1> 	;	are different (user's registers are saved to 
  4194                              <1> 	;	and then restored from system's stack.)
  4195                              <1> 	;
  4196                              <1> 	;	NOTE: Retro UNIX 8086 v1 'arg2' routine gets these
  4197                              <1> 	;	      arguments which were in these registers;
  4198                              <1> 	;	      but, it returns by putting the 1st argument
  4199                              <1> 	;	      in 'u.namep' and the 2nd argument
  4200                              <1> 	;	      on top of stack. (1st argument is offset of the
  4201                              <1> 	;	      file/path name in the user's program segment.)		 	
  4202                              <1> 	
  4203                              <1> 	;call	arg2
  4204                              <1> 	; * name - 'u.namep' points to address of file/path name
  4205                              <1> 	;          in the user's program segment ('u.segmnt')
  4206                              <1> 	;          with offset in BX register (as sysopen argument 1).
  4207                              <1> 	; * argp - sysexec argument 2 is in CX register 
  4208                              <1> 	;          which is on top of stack.
  4209                              <1> 	;
  4210                              <1> 		; jsr r0,arg2 / arg0 in u.namep,arg1 on top of stack
  4211                              <1> 
  4212                              <1> 	; 23/06/2015 (32 bit modifications)
  4213                              <1> 
  4214                              <1> 	;; 13/11/2017
  4215                              <1> 	;;mov	[u.namep], ebx ; argument 1
  4216                              <1>         ; 18/10/2015
  4217 0000E089 890D[4C040300]      <1> 	mov     [argv], ecx  ; * ; argument 2
  4218                              <1> 
  4219                              <1> 	; 13/11/2017
  4220 0000E08F 89DE                <1> 	mov	esi, ebx
  4221 0000E091 E84E210000          <1> 	call	set_working_path_x
  4222 0000E096 7319                <1> 	jnc	short sysexec_0
  4223                              <1> 
  4224                              <1> 	;; 'bad command or file name'
  4225                              <1> 	;mov	eax, ERR_BAD_CMD_ARG ; 01h ; TRDOS 8086
  4226                              <1> 	
  4227                              <1> 	; 'file not found !' error
  4228 0000E098 B802000000          <1> 	mov	eax, ERR_NOT_FOUND ; 02h ; TRDOS 8086
  4229                              <1> sysexec_not_found_err:
  4230                              <1> sysexec_access_error:
  4231                              <1> sysexec_ext_error:
  4232 0000E09D A3[64030300]        <1> 	mov	[u.r0], eax
  4233 0000E0A2 A3[C8030300]        <1> 	mov	[u.error], eax
  4234 0000E0A7 E80D220000          <1> 	call 	reset_working_path
  4235 0000E0AC E9C9EEFFFF          <1> 	jmp	error
  4236                              <1> 
  4237                              <1> sysexec_0:
  4238                              <1> 	; 13/11/2017
  4239                              <1> 	;mov	esi, FindFile_Name
  4240 0000E0B1 66B80018            <1>         mov	ax, 1800h ; Only files 
  4241 0000E0B5 E865AAFFFF          <1> 	call	find_first_file
  4242 0000E0BA 72E1                <1> 	jc	short sysexec_not_found_err ; eax = 2
  4243                              <1> 
  4244                              <1> 	; check_ file attributes
  4245                              <1> 	; (attribute bits = 00ADVSHR) ; 18h = Directory+Volume
  4246                              <1> 	; BL = Attributes byte
  4247                              <1> 	
  4248 0000E0BC F6C306              <1>         test	bl, 6  ; system file or hidden file (S+H) 
  4249                              <1> 	;jz	short sysexec_0ext
  4250 0000E0BF 7417                <1> 	jz	short sysexec_1 ; yes
  4251                              <1> 
  4252                              <1> 	; 13/11/2017 
  4253                              <1> 	; /// TRDOS386 permission check for multiuser mode ///
  4254                              <1> 	; SYSTEM file or HIDDEN file !!
  4255                              <1> 	; (Only super user has permission to run this file.)
  4256                              <1> 	
  4257                              <1> 	; ([u.uid]=0 for super user or root in multiuser mode)  
  4258                              <1> 	; ([u.uid]=0 for any users in singleuser mode) 
  4259 0000E0C1 803D[B0030300]00    <1> 	cmp 	byte [u.uid], 0 ; Super User ([u.uid]=0) ?
  4260                              <1> 	;jna	short sysexec_0ext
  4261 0000E0C8 760E                <1> 	jna	short sysexec_1 ; yes 
  4262                              <1> 
  4263                              <1> 	; 'permission denied !' error  
  4264 0000E0CA B80B000000          <1>         mov	eax, ERR_FILE_ACCESS  ; 11 = ERR_PERM_DENIED
  4265 0000E0CF EBCC                <1>         jmp	short sysexec_access_error
  4266                              <1> 
  4267                              <1> sysexec_not_exf:
  4268                              <1> 	; 'not executable file !' error
  4269 0000E0D1 B816000000          <1> 	mov	eax, ERR_NOT_EXECUTABLE
  4270 0000E0D6 EBC5                <1> 	jmp	sysexec_ext_error
  4271                              <1> 
  4272                              <1> ;sysexec_0ext:
  4273                              <1> sysexec_1:
  4274                              <1> 	; 18/11/2017
  4275 0000E0D8 BE[28680100]        <1> 	mov	esi, FindFile_Name
  4276                              <1> 	; 13/11/2017
  4277                              <1> 	; check program file name extension
  4278                              <1> 	; ('.PRG' for current TRDOS version)
  4279 0000E0DD E8E0C4FFFF          <1> 	call	check_prg_filename_ext
  4280 0000E0E2 72ED                <1> 	jc	short sysexec_not_exf
  4281                              <1> 	
  4282                              <1> 	; 18/11/2017
  4283 0000E0E4 3C50                <1> 	cmp	al, 'P'
  4284 0000E0E6 75E9                <1> 	jne	short sysexec_not_exf	
  4285                              <1> 
  4286                              <1> 	; '.PRG' extension is OK.
  4287                              <1> 	; Only '.PRG' files are valid program files
  4288                              <1> 	; for current TRDOS 386 version.
  4289                              <1> 
  4290 0000E0E8 8B15[54680100]      <1> 	mov	edx, [FindFile_DirEntry+DirEntry_FileSize]
  4291 0000E0EE 66A1[4C680100]      <1> 	mov	ax, [FindFile_DirEntry+DirEntry_FstClusHI]
  4292 0000E0F4 C1E010              <1> 	shl	eax, 16
  4293 0000E0F7 66A1[52680100]      <1> 	mov	ax, [FindFile_DirEntry+DirEntry_FstClusLO]
  4294                              <1> 	; EAX = First Cluster number
  4295                              <1> 	; EDX = File Size
  4296                              <1> 
  4297 0000E0FD A3[51040300]        <1> 	mov	[ii], eax
  4298 0000E102 8915[55040300]      <1> 	mov	[i.size], edx
  4299                              <1> 
  4300                              <1> ;sysexec_1:
  4301                              <1> 	; 13/11/2017 - TRDOS 386 (TRDOS v2.0)
  4302                              <1> 	; 24/06/2015 - 23/10/2015 (Retro UNIX 386 v1)
  4303                              <1>         ; Moving arguments to the end of [u.upage]
  4304                              <1> 	; (by regarding page borders in user's memory space)
  4305                              <1> 	;
  4306                              <1> 	; 10/10/2015
  4307                              <1> 	; 21/07/2015
  4308 0000E108 89E5                <1> 	mov	ebp, esp ; (**)
  4309                              <1> 	; 18/10/2015
  4310 0000E10A 89EF                <1> 	mov 	edi, ebp
  4311 0000E10C B900010000          <1> 	mov 	ecx, MAX_ARG_LEN ; 256
  4312                              <1> 	;sub	edi, MAX_ARG_LEN ; 256
  4313 0000E111 29CF                <1> 	sub	edi, ecx
  4314 0000E113 89FC                <1> 	mov	esp, edi ; *!*
  4315 0000E115 31C0                <1> 	xor	eax, eax
  4316 0000E117 A3[8C030300]        <1> 	mov 	[u.nread], eax ; 0
  4317 0000E11C 66A3[4A040300]      <1> 	mov	[argc], ax ; 0 ; 13/11/2017
  4318 0000E122 49                  <1> 	dec	ecx ; 256 - 1
  4319 0000E123 890D[88030300]      <1> 	mov 	[u.count], ecx ; MAX_ARG_LEN - 1 ; 255
  4320                              <1> 	;mov 	dword [u.count], MAX_ARG_LEN - 1 ; 255
  4321                              <1> sysexec_2:
  4322 0000E129 8B35[4C040300]      <1> 	mov	esi, [argv] ; 18/10/2015 
  4323 0000E12F E866000000          <1> 	call	get_argp
  4324 0000E134 B904000000          <1> 	mov	ecx, 4 ; mov ecx, 4
  4325                              <1> sysexec_3:
  4326 0000E139 21C0                <1> 	and	eax, eax
  4327 0000E13B 0F8429050000        <1>         jz      sysexec_6
  4328                              <1> 	; 18/10/2015
  4329 0000E141 010D[4C040300]      <1> 	add	[argv], ecx ; 4
  4330 0000E147 66FF05[4A040300]    <1> 	inc	word [argc]
  4331                              <1> 	;
  4332 0000E14E A3[84030300]        <1> 	mov	[u.base], eax
  4333                              <1>  	; 23/10/2015
  4334 0000E153 66C705[C4030300]00- <1> 	mov	word [u.pcount], 0
  4334 0000E15B 00                  <1>
  4335                              <1> sysexec_4:
  4336 0000E15C E8A10B0000          <1> 	call	cpass ; get a character from user's core memory
  4337 0000E161 750E                <1>         jnz	short sysexec_5
  4338                              <1> 		; (max. 255 chars + null)
  4339                              <1> 	; 18/10/2015
  4340 0000E163 28C0                <1> 	sub 	al, al
  4341 0000E165 AA                  <1> 	stosb
  4342 0000E166 FF05[8C030300]      <1> 	inc	dword [u.nread]
  4343 0000E16C E9F9040000          <1> 	jmp	sysexec_6 ; 24/04/2016
  4344                              <1> sysexec_5:
  4345 0000E171 AA                  <1> 	stosb
  4346 0000E172 20C0                <1> 	and 	al, al
  4347 0000E174 75E6                <1> 	jnz	short sysexec_4
  4348 0000E176 B904000000          <1> 	mov	ecx, 4
  4349 0000E17B 390D[48040300]      <1> 	cmp	[ncount], ecx ; 4
  4350 0000E181 72A6                <1> 	jb	short sysexec_2
  4351 0000E183 8B35[44040300]      <1> 	mov	esi, [nbase]
  4352 0000E189 010D[44040300]      <1> 	add	[nbase], ecx ; 4	
  4353 0000E18F 66290D[48040300]    <1> 	sub	[ncount], cx 
  4354 0000E196 8B06                <1> 	mov	eax, [esi]
  4355 0000E198 EB9F                <1> 	jmp	short sysexec_3
  4356                              <1> 
  4357                              <1> get_argp:
  4358                              <1> 	; 14/11/2017 - TRDOS 386 (TRDOS v2.0)
  4359                              <1> 	; 18/10/2015 (nbase, ncount)
  4360                              <1> 	; 21/07/2015
  4361                              <1> 	; 24/06/2015 (Retro UNIX 386 v1)
  4362                              <1> 	; Get (virtual) address of argument from user's core memory
  4363                              <1> 	;
  4364                              <1> 	; INPUT:
  4365                              <1> 	;	esi = virtual address of argument pointer
  4366                              <1> 	; OUTPUT:
  4367                              <1> 	;	eax = virtual address of argument
  4368                              <1> 	;
  4369                              <1> 	; Modified registers: EAX, EBX, ECX, EDX, ESI 
  4370                              <1> 	;
  4371 0000E19A 833D[BC030300]00    <1>  	cmp     dword [u.ppgdir], 0 ; /etc/init ?
  4372                              <1> 				    ; (the caller is kernel)
  4373 0000E1A1 7667                <1>         jna     short get_argpk 
  4374                              <1> 	;
  4375 0000E1A3 89F3                <1>      	mov	ebx, esi
  4376 0000E1A5 E85078FFFF          <1> 	call	get_physical_addr ; get physical address
  4377 0000E1AA 0F8289000000        <1>         jc      get_argp_err
  4378 0000E1B0 A3[44040300]        <1> 	mov 	[nbase], eax ; physical address	
  4379 0000E1B5 66890D[48040300]    <1> 	mov	[ncount], cx ; remain byte count in page (1-4096)
  4380 0000E1BC B804000000          <1> 	mov	eax, 4 ; 21/07/2015
  4381 0000E1C1 6639C1              <1> 	cmp	cx, ax ; 4
  4382 0000E1C4 735D                <1> 	jnb	short get_argp2
  4383 0000E1C6 89F3                <1> 	mov	ebx, esi
  4384 0000E1C8 01CB                <1> 	add	ebx, ecx
  4385 0000E1CA E82B78FFFF          <1> 	call	get_physical_addr ; get physical address
  4386 0000E1CF 7268                <1> 	jc	short get_argp_err
  4387                              <1> 	;push	esi
  4388 0000E1D1 89C6                <1> 	mov	esi, eax
  4389 0000E1D3 66870D[48040300]    <1> 	xchg	cx, [ncount]
  4390 0000E1DA 8735[44040300]      <1> 	xchg	esi, [nbase]
  4391 0000E1E0 B504                <1> 	mov	ch, 4
  4392 0000E1E2 28CD                <1> 	sub	ch, cl
  4393                              <1> get_argp0:
  4394 0000E1E4 AC                  <1> 	lodsb
  4395 0000E1E5 6650                <1> 	push	ax
  4396 0000E1E7 FEC9                <1> 	dec	cl
  4397 0000E1E9 75F9                <1>         jnz     short get_argp0
  4398 0000E1EB 8B35[44040300]      <1> 	mov	esi, [nbase]
  4399                              <1> 	; 21/07/2015
  4400 0000E1F1 0FB6C5              <1> 	movzx	eax, ch
  4401 0000E1F4 0105[44040300]      <1> 	add	[nbase], eax
  4402 0000E1FA 662905[48040300]    <1> 	sub	[ncount], ax
  4403                              <1> get_argp1:
  4404 0000E201 AC                  <1> 	lodsb
  4405 0000E202 FECD                <1> 	dec	ch
  4406 0000E204 7447                <1>         jz      short get_argp3
  4407 0000E206 6650                <1>         push	ax
  4408 0000E208 EBF7                <1> 	jmp     short get_argp1
  4409                              <1> get_argpk:
  4410                              <1> 	; Argument is in kernel's memory space
  4411 0000E20A 66C705[48040300]00- <1> 	mov	word [ncount], PAGE_SIZE ; 4096
  4411 0000E212 10                  <1>
  4412 0000E213 8935[44040300]      <1> 	mov	[nbase], esi
  4413 0000E219 8305[44040300]04    <1> 	add	dword [nbase], 4
  4414 0000E220 8B06                <1> 	mov	eax, [esi] ; virtual addr. = physcal addr.
  4415 0000E222 C3                  <1> 	retn
  4416                              <1> get_argp2:
  4417                              <1> 	; 21/07/2015
  4418                              <1> 	;mov	eax, 4
  4419 0000E223 8B15[44040300]      <1> 	mov 	edx, [nbase] ; 18/10/2015
  4420 0000E229 0105[44040300]      <1> 	add	[nbase], eax
  4421 0000E22F 662905[48040300]    <1> 	sub	[ncount], ax
  4422                              <1> 	;
  4423 0000E236 8B02                <1> 	mov	eax, [edx]
  4424 0000E238 C3                  <1> 	retn
  4425                              <1> get_argp_err:
  4426 0000E239 A3[C8030300]        <1> 	mov	[u.error], eax
  4427                              <1> 	; 14/11/2017
  4428 0000E23E B801000000          <1> 	mov	eax, ERR_BAD_CMD_ARG ; 01h ; TRDOS 8086
  4429 0000E243 A3[64030300]        <1> 	mov	[u.r0], eax
  4430 0000E248 E92DEDFFFF          <1> 	jmp	error
  4431                              <1> get_argp3:
  4432 0000E24D B103                <1> 	mov	cl, 3
  4433                              <1> get_argp4:
  4434 0000E24F C1E008              <1> 	shl	eax, 8
  4435 0000E252 665A                <1> 	pop	dx
  4436 0000E254 88D0                <1> 	mov 	al, dl
  4437 0000E256 E2F7                <1>         loop    get_argp4
  4438                              <1> 	;pop	esi
  4439 0000E258 C3                  <1> 	retn	
  4440                              <1> 
  4441                              <1> sysstat: 
  4442                              <1> 	; 13/01/2017 - TRDOS 386 (TRDOS v2.0)
  4443                              <1> 	; temporary !
  4444 0000E259 B801000000          <1> 	mov	eax, ERR_INV_FNUMBER ; 'invalid function number !'
  4445 0000E25E A3[C8030300]        <1>         mov     [u.error], eax
  4446 0000E263 A3[64030300]        <1>         mov     [u.r0], eax 
  4447 0000E268 E90DEDFFFF          <1> 	jmp	error
  4448                              <1> 
  4449                              <1> sysfstat: 
  4450                              <1> 	; 13/01/2017 - TRDOS 386 (TRDOS v2.0)
  4451                              <1> 	; temporary !
  4452 0000E26D B801000000          <1> 	mov	eax, ERR_INV_FNUMBER ; 'invalid function number !'
  4453 0000E272 A3[C8030300]        <1>         mov     [u.error], eax
  4454 0000E277 A3[64030300]        <1>         mov     [u.r0], eax 
  4455 0000E27C E9F9ECFFFF          <1> 	jmp	error
  4456                              <1> 
  4457                              <1> fclose:
  4458                              <1> 	; 06/10/2016 (TRDOS 386 = TRDOS v2.0)
  4459                              <1> 	;
  4460                              <1> 	; 18/06/2015 (Retro UNIX 386 v1 - Beginning)
  4461                              <1> 	;            (32 bit offset pointer modification)
  4462                              <1> 	; 19/04/2013 - 12/01/2014 (Retro UNIX 8086 v1)
  4463                              <1> 	;
  4464                              <1> 	; Given the file descriptor (index to the u.fp list)
  4465                              <1> 	; 'fclose' first gets the i-number of the file via 'getf'.
  4466                              <1> 	; If i-node is active (i-number > 0) the entry in 
  4467                              <1> 	; u.fp list is cleared. If all the processes that opened
  4468                              <1> 	; that file close it, then fsp etry is freed and the file
  4469                              <1> 	; is closed. If not a return is taken. 
  4470                              <1> 	; If the file has been deleted while open, 'anyi' is called
  4471                              <1> 	; to see anyone else has it open, i.e., see if it is appears
  4472                              <1> 	; in another entry in the fsp table. Upon return from 'anyi'
  4473                              <1> 	; a check is made to see if the file is special.	
  4474                              <1> 	;
  4475                              <1> 	; INPUTS ->
  4476                              <1> 	;    r1 - contains the file descriptor (value=0,1,2...)
  4477                              <1> 	;    u.fp - list of entries in the fsp table
  4478                              <1> 	;    fsp - table of entries (4 words/entry) of open files.	 
  4479                              <1> 	; OUTPUTS ->
  4480                              <1> 	;    r1 - contains the same file descriptor
  4481                              <1> 	;    r2 - contains i-number
  4482                              <1> 	;
  4483                              <1> 	; ((AX = R1))
  4484                              <1> 	; ((Modified registers: eDX, eBX, eCX, eSI, eDI, eBP))
  4485                              <1> 	;
  4486                              <1> 	; Retro UNIX 8086 v1 modification : CF = 1
  4487                              <1> 	;              if i-number of the file is 0. (error)  	
  4488                              <1> 	;
  4489                              <1> 	; TRDOS 386 (06/10/2016)
  4490                              <1> 	; 
  4491                              <1> 	; INPUT:
  4492                              <1> 	;	EAX = File Handle (File Descriptor, File Index)
  4493                              <1> 	;
  4494                              <1> 	; OUTPUT:
  4495                              <1> 	;	CF = 1 -> File not open !
  4496                              <1> 	;	CF = 0 -> OK!
  4497                              <1> 	;	     EBX = File Number (System)
  4498                              <1> 	;	     [cdev] = Logical DOS Drive Number
  4499                              <1> 	;	     EAX = File Handle/Number (user) 	
  4500                              <1> 	;
  4501                              <1> 	; Modified Registers: EBX
  4502                              <1> 
  4503 0000E281 50                  <1> 	push	eax ; File handle
  4504                              <1> 	
  4505 0000E282 E846000000          <1> 	call	getf
  4506 0000E287 0F8205240000        <1> 	jc	device_close ; eax = device number
  4507                              <1> 
  4508 0000E28D 80BB[A66E0100]01    <1> 	cmp	byte [ebx+OF_MODE], 1 ; open mode ; 0 = empty entry
  4509 0000E294 722E                <1> 	jb	short fclose_1	      ; 1 = read, 2 = write
  4510                              <1> 	
  4511 0000E296 83F801              <1> 	cmp	eax, 1 ; is the first cluster number > 0
  4512 0000E299 7229                <1> 	jb	short fclose_1 ; no, this is empty entry
  4513                              <1> 
  4514                              <1> fclose_0:
  4515 0000E29B FE8B[BA6E0100]      <1> 	dec	byte [ebx+OF_OPENCOUNT] ; decrement the number of processes 
  4516                              <1> 			                ; that have opened the file
  4517 0000E2A1 7921                <1> 	jns	short fclose_1 ; jump if not negative (jump if bit 7 is 0)	 
  4518                              <1> 			; if all processes haven't closed the file, return
  4519                              <1> 	;
  4520                              <1> 	; eax ; First cluster
  4521 0000E2A3 31C0                <1> 	xor	eax, eax ; 0
  4522 0000E2A5 8883[A66E0100]      <1> 	mov	[ebx+OF_MODE], al ; 0 = empty entry
  4523                              <1> 	;mov	[ebx+OF_STATUS], al ; 0 = empty entry
  4524 0000E2AB 66C1E302            <1> 	shl	bx, 2 
  4525 0000E2AF 8983[746E0100]      <1> 	mov	[ebx+OF_FCLUSTER], eax ; 0
  4526 0000E2B5 8983[8C6F0100]      <1> 	mov	[ebx+OF_CCLUSTER], eax ; 0
  4527                              <1> 	;mov	[ebx+OF_CCINDEX], eax ; 0
  4528 0000E2BB A3[74030300]        <1> 	mov	[u.fofp], eax ; 0
  4529 0000E2C0 66C1EB02            <1> 	shr	bx, 2
  4530                              <1> fclose_1: ; 1:
  4531 0000E2C4 58                  <1> 	pop	eax ; File handle (File Descriptor, File Index)
  4532 0000E2C5 C680[6A030300]00    <1> 	mov	byte [eax+u.fp], 0 ; clear that entry in the u.fp list
  4533 0000E2CC C3                  <1> 	retn
  4534                              <1> 
  4535                              <1> getf:
  4536                              <1> 	; 12/10/2016
  4537                              <1> 	; 11/10/2016
  4538                              <1> 	; 08/10/2016
  4539                              <1> 	; 06/10/2016 (TRDOS 386 = TRDOS v2.0)
  4540                              <1> 	; / get the device number and the i-number of an open file
  4541                              <1> 	; 13/05/2015
  4542                              <1> 	; 11/05/2015 (Retro UNIX 386 v1 - Beginning)
  4543                              <1> 	; 19/04/2013 - 18/11/2013 (Retro UNIX 8086 v1)
  4544                              <1> 	;
  4545 0000E2CD 89C3                <1> 	mov	ebx, eax
  4546                              <1> getf1: 
  4547 0000E2CF 83FB0A              <1> 	cmp	ebx, 10
  4548 0000E2D2 730A                <1>         jnb	short getf2
  4549 0000E2D4 8A9B[6A030300]      <1> 	mov	bl, [ebx+u.fp]
  4550 0000E2DA 08DB                <1> 	or	bl, bl
  4551 0000E2DC 7503                <1> 	jnz	short getf3
  4552                              <1> getf2:
  4553                              <1> 	; 'File not open !' error (ax=0)
  4554 0000E2DE 29C0                <1> 	sub	eax, eax
  4555 0000E2E0 C3                  <1> 	retn
  4556                              <1> getf3:	
  4557 0000E2E1 F6C380              <1> 	test	bl, 80h
  4558 0000E2E4 7530                <1> 	jnz	short getf5 ; device
  4559 0000E2E6 FECB                <1> 	dec	bl ; 0 based
  4560 0000E2E8 8A83[9C6E0100]      <1> 	mov	al, [ebx+OF_DRIVE]
  4561 0000E2EE A2[46030300]        <1> 	mov	[cdev], al
  4562 0000E2F3 C0E302              <1> 	shl	bl, 2 ; *4 (dword offset)
  4563 0000E2F6 8B83[EC6E0100]      <1> 	mov	eax, [ebx+OF_SIZE]
  4564 0000E2FC A3[55040300]        <1> 	mov	[i.size], eax ; file size
  4565 0000E301 8D83[C46E0100]      <1> 	lea	eax, [ebx+OF_POINTER] ;12/10/2016
  4566 0000E307 A3[74030300]        <1> 	mov	[u.fofp], eax
  4567 0000E30C 8B83[746E0100]      <1> 	mov	eax, [ebx+OF_FCLUSTER]
  4568 0000E312 C0EB02              <1> 	shr	bl, 2 ; /4 (byte offset) 
  4569                              <1> getf4:
  4570 0000E315 C3                  <1> 	retn
  4571                              <1> getf5: 
  4572                              <1> 	; get device number
  4573 0000E316 80E37F              <1> 	and	bl, 7Fh ; 1 to 7Fh
  4574 0000E319 FECB                <1> 	dec	bl ; 0 based (0 to 7Eh)
  4575 0000E31B 8A83[CE6C0100]      <1> 	mov	al, [ebx+DEV_DRIVER]
  4576 0000E321 8AAB[386C0100]      <1> 	mov	ch, [ebx+DEV_ACCESS]
  4577 0000E327 8A8B[EC6C0100]      <1> 	mov	cl, [ebx+DEV_OPENMODE]
  4578 0000E32D 80E5FE              <1> 	and	ch, 0FEh ; reset bit 0 ; dev_close
  4579 0000E330 F9                  <1> 	stc ; cf = 1 
  4580 0000E331 C3                  <1> 	retn	
  4581                              <1> 
  4582                              <1> trans_addr_nmbp:
  4583                              <1> 	; 18/10/2015
  4584                              <1> 	; 12/10/2015
  4585 0000E332 8B2D[7C030300]      <1> 	mov 	ebp, [u.namep]
  4586                              <1> trans_addr_nm: 
  4587                              <1> 	; Convert virtual (pathname) address to physical address
  4588                              <1> 	; (Retro UNIX 386 v1 feature only !)
  4589                              <1> 	; 18/10/2015
  4590                              <1> 	; 12/10/2015 (u.pnbase & u.pncount has been removed from code)
  4591                              <1> 	; 02/07/2015
  4592                              <1> 	; 17/06/2015
  4593                              <1> 	; 16/06/2015
  4594                              <1> 	;
  4595                              <1> 	; INPUTS: 
  4596                              <1> 	;	ebp = pathname address (virtual) ; [u.namep]
  4597                              <1> 	;	[u.pgdir] = user's page directory
  4598                              <1> 	; OUTPUT:
  4599                              <1> 	;       esi = physical address of the pathname
  4600                              <1> 	;	ecx = remain byte count in the page
  4601                              <1> 	;
  4602                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX, ESI)
  4603                              <1> 	;
  4604 0000E338 833D[BC030300]00    <1>         cmp     dword [u.ppgdir], 0  ; /etc/init ? (sysexec)
  4605 0000E33F 7618                <1> 	jna	short trans_addr_nmk ; the caller is os kernel;
  4606                              <1> 				     ; it is already physical address
  4607 0000E341 50                  <1>    	push	eax	
  4608 0000E342 89EB                <1> 	mov	ebx, ebp ; [u.namep] ; pathname address (virtual)
  4609 0000E344 E8B176FFFF          <1>        	call	get_physical_addr ; get physical address
  4610 0000E349 7204                <1> 	jc	short tr_addr_nm_err
  4611                              <1> 	; 18/10/2015
  4612                              <1> 	; eax = physical address 
  4613                              <1> 	; cx = remain byte count in page (1-4096) 
  4614                              <1> 		; 12/10/2015 (cx = [u.pncount])
  4615 0000E34B 89C6                <1> 	mov	esi, eax ; 12/10/2015 (esi=[u.pnbase])
  4616 0000E34D 58                  <1> 	pop	eax 
  4617 0000E34E C3                  <1> 	retn
  4618                              <1> 
  4619                              <1> tr_addr_nm_err:
  4620 0000E34F A3[C8030300]        <1> 	mov	[u.error], eax
  4621                              <1> 	;pop 	eax
  4622 0000E354 E921ECFFFF          <1> 	jmp	error
  4623                              <1> 
  4624                              <1> trans_addr_nmk:
  4625                              <1> 	; 12/10/2015
  4626                              <1> 	; 02/07/2015
  4627 0000E359 8B35[7C030300]      <1> 	mov	esi, [u.namep]  ; [u.pnbase]
  4628 0000E35F 66B90010            <1> 	mov	cx, PAGE_SIZE ; 4096 ; [u.pncount]
  4629 0000E363 C3                  <1> 	retn
  4630                              <1> 
  4631                              <1> 
  4632                              <1> sysbreak:
  4633                              <1> 	; 18/10/2015
  4634                              <1> 	; 07/10/2015
  4635                              <1> 	; 23/06/2015 (Retro UNIX 386 v1 - Beginning)
  4636                              <1> 	; 20/06/2013 - 24/03/2014 (Retro UNIX 8086 v1)
  4637                              <1> 	;
  4638                              <1> 	; 'sysbreak' sets the programs break points. 
  4639                              <1> 	; It checks the current break point (u.break) to see if it is
  4640                              <1> 	; between "core" and the stack (sp). If it is, it is made an
  4641                              <1> 	; even address (if it was odd) and the area between u.break
  4642                              <1> 	; and the stack is cleared. The new breakpoint is then put
  4643                              <1> 	; in u.break and control is passed to 'sysret'.
  4644                              <1> 	;
  4645                              <1> 	; Calling sequence:
  4646                              <1> 	;	sysbreak; addr
  4647                              <1> 	; Arguments: -
  4648                              <1> 	;	
  4649                              <1> 	; Inputs: u.break - current breakpoint
  4650                              <1> 	; Outputs: u.break - new breakpoint 
  4651                              <1> 	;	area between old u.break and the stack (sp) is cleared.
  4652                              <1> 	; ...............................................................
  4653                              <1> 	;	
  4654                              <1> 	; Retro UNIX 8086 v1 modification:
  4655                              <1> 	;	The user/application program puts breakpoint address
  4656                              <1> 	;       in BX register as 'sysbreak' system call argument.
  4657                              <1> 	; 	(argument transfer method 1)
  4658                              <1> 	;
  4659                              <1> 	;  NOTE: Beginning of core is 0 in Retro UNIX 8086 v1 !
  4660                              <1> 	; 	((!'sysbreak' is not needed in Retro UNIX 8086 v1!))
  4661                              <1> 	;  NOTE:
  4662                              <1> 	; 	'sysbreak' clears extended part (beyond of previous
  4663                              <1> 	;	'u.break' address) of user's memory for original unix's
  4664                              <1> 	;	'bss' compatibility with Retro UNIX 8086 v1 (19/11/2013)
  4665                              <1> 
  4666                              <1> 		; mov u.break,r1 / move users break point to r1
  4667                              <1> 		; cmp r1,$core / is it the same or lower than core?
  4668                              <1> 		; blos 1f / yes, 1f
  4669                              <1> 	; 23/06/2015
  4670 0000E364 8B2D[90030300]      <1> 	mov	ebp, [u.break] ; virtual address (offset)
  4671                              <1> 	;and	ebp, ebp
  4672                              <1> 	;jz	short sysbreak_3 
  4673                              <1> 	; Retro UNIX 386 v1 NOTE: u.break points to virtual address !!!
  4674                              <1> 	; (Even break point address is not needed for Retro UNIX 386 v1)
  4675 0000E36A 8B15[5C030300]      <1> 	mov	edx, [u.sp] ; kernel stack at the beginning of sys call
  4676 0000E370 83C20C              <1> 	add	edx, 12 ; EIP -4-> CS -4-> EFLAGS -4-> ESP (user) 
  4677                              <1> 	; 07/10/2015
  4678 0000E373 891D[90030300]      <1> 	mov	[u.break], ebx ; virtual address !!!
  4679                              <1> 	;
  4680 0000E379 3B1A                <1> 	cmp	ebx, [edx] ; compare new break point with 
  4681                              <1> 			   ; with top of user's stack (virtual!)
  4682 0000E37B 7323                <1> 	jnb	short sysbreak_3
  4683                              <1> 		; cmp r1,sp / is it the same or higher 
  4684                              <1> 			  ; / than the stack?
  4685                              <1> 		; bhis 1f / yes, 1f
  4686 0000E37D 89DE                <1> 	mov	esi, ebx
  4687 0000E37F 29EE                <1> 	sub	esi, ebp ; new break point - old break point
  4688 0000E381 761D                <1> 	jna	short sysbreak_3 
  4689                              <1> 	;push	ebx
  4690                              <1> sysbreak_1:
  4691 0000E383 89EB                <1> 	mov	ebx, ebp  
  4692 0000E385 E87076FFFF          <1> 	call	get_physical_addr ; get physical address
  4693 0000E38A 72C3                <1> 	jc	tr_addr_nm_err
  4694                              <1> 	; 18/10/2015
  4695 0000E38C 89C7                <1> 	mov	edi, eax 
  4696 0000E38E 29C0                <1> 	sub	eax, eax ; 0
  4697                              <1> 		 ; ECX = remain byte count in page (1-4096)
  4698 0000E390 39CE                <1> 	cmp	esi, ecx
  4699 0000E392 7302                <1> 	jnb	short sysbreak_2
  4700 0000E394 89F1                <1> 	mov	ecx, esi
  4701                              <1> sysbreak_2:
  4702 0000E396 29CE                <1> 	sub	esi, ecx
  4703 0000E398 01CD                <1> 	add	ebp, ecx
  4704 0000E39A F3AA                <1> 	rep 	stosb
  4705 0000E39C 09F6                <1> 	or	esi, esi
  4706 0000E39E 75E3                <1> 	jnz	short sysbreak_1
  4707                              <1> 	;
  4708                              <1> 		; bit $1,r1 / is it an odd address
  4709                              <1> 		; beq 2f / no, its even
  4710                              <1> 		; clrb (r1)+ / yes, make it even
  4711                              <1> 	; 2: / clear area between the break point and the stack
  4712                              <1> 		; cmp r1,sp / is it higher or same than the stack
  4713                              <1> 		; bhis 1f / yes, quit
  4714                              <1> 		; clr (r1)+ / clear word
  4715                              <1> 		; br 2b / go back
  4716                              <1> 	;pop	ebx
  4717                              <1> sysbreak_3: ; 1:
  4718                              <1> 	;mov	[u.break], ebx ; virtual address !!!
  4719                              <1> 		; jsr r0,arg; u.break / put the "address" 
  4720                              <1> 			; / in u.break (set new break point)
  4721                              <1> 		; br sysret4 / br sysret
  4722 0000E3A0 E9F5EBFFFF          <1> 	jmp	sysret
  4723                              <1> 
  4724                              <1> sysseek: ; / moves read write pointer in an fsp entry
  4725                              <1> 	; 06/11/2016 - TRDOS 386 (TRDOS v2.0)
  4726                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4727                              <1> 	; 07/07/2013 - 05/08/2013 (Retro UNIX 8086 v1)
  4728                              <1> 	;
  4729                              <1> 	; 'sysseek' changes the r/w pointer of (3rd word of in an
  4730                              <1> 	; fsp entry) of an open file whose file descriptor is in u.r0.
  4731                              <1> 	; The file descriptor refers to a file open for reading or
  4732                              <1> 	; writing. The read (or write) pointer is set as follows:
  4733                              <1> 	;	* if 'ptrname' is 0, the pointer is set to offset.
  4734                              <1> 	;	* if 'ptrname' is 1, the pointer is set to its
  4735                              <1> 	;	  current location plus offset.
  4736                              <1> 	;	* if 'ptrname' is 2, the pointer is set to the
  4737                              <1> 	;	  size of file plus offset.
  4738                              <1> 	; The error bit (e-bit) is set for an undefined descriptor.
  4739                              <1> 	;
  4740                              <1> 	; Calling sequence:
  4741                              <1> 	;	sysseek; offset; ptrname
  4742                              <1> 	; Arguments:
  4743                              <1> 	;	offset - number of bytes desired to move 
  4744                              <1> 	;		 the r/w pointer
  4745                              <1> 	;	ptrname - a switch indicated above
  4746                              <1> 	;
  4747                              <1> 	; Inputs: r0 - file descriptor 
  4748                              <1> 	; Outputs: -
  4749                              <1> 	; ...............................................................
  4750                              <1> 	;	
  4751                              <1> 	; Retro UNIX 8086 v1 modification: 
  4752                              <1> 	;       'sysseek' system call has three arguments; so,
  4753                              <1> 	;	* 1st argument, file descriptor is in BX (BL) register
  4754                              <1> 	;	* 2nd argument, offset is in CX register
  4755                              <1> 	;	* 3rd argument, ptrname/switch is in DX (DL) register	
  4756                              <1> 
  4757 0000E3A5 E821000000          <1> 	call	seektell
  4758                              <1> 	; EAX = Current R/W pointer of the file
  4759                              <1> 	; EBX = [u.fofp]
  4760                              <1> 	; [u.base] = offset (ECX input)
  4761                              <1> 
  4762 0000E3AA 0305[84030300]      <1> 	add	eax, [u.base]
  4763 0000E3B0 8903                <1> 	mov	[ebx], eax
  4764 0000E3B2 E9E3EBFFFF          <1> 	jmp	sysret
  4765                              <1> 
  4766                              <1> systell: ; / get the r/w pointer
  4767                              <1> 	; 06/11/2016 - TRDOS 386 (TRDOS v2.0) - temporary !-
  4768                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4769                              <1> 	; 07/07/2013 - 05/08/2013 (Retro UNIX 8086 v1)
  4770                              <1> 	;
  4771                              <1> 	; Retro UNIX 8086 v1 modification:
  4772                              <1> 	; ! 'systell' does not work in original UNIX v1,
  4773                              <1> 	; 	    it returns with error !
  4774                              <1> 	; Inputs: r0 - file descriptor 
  4775                              <1> 	; Outputs: r0 - file r/w pointer
  4776                              <1> 
  4777                              <1> 	;xor	ecx, ecx ; 0
  4778 0000E3B7 BA01000000          <1> 	mov	edx, 1 ; 05/08/2013
  4779                              <1> 	;call 	seektell
  4780 0000E3BC E810000000          <1> 	call 	seektell0 ; 05/08/2013
  4781                              <1> 	;; 06/11/2016
  4782                              <1> 	;; mov	eax, [ebx]
  4783 0000E3C1 A3[64030300]        <1> 	mov	[u.r0], eax
  4784 0000E3C6 E9CFEBFFFF          <1> 	jmp	sysret
  4785                              <1> 
  4786                              <1> ; Original unix v1 'systell' system call:
  4787                              <1> 		; jsr r0,seektell
  4788                              <1> 		; br error4
  4789                              <1> 
  4790                              <1> seektell:
  4791                              <1> 	; 06/11/2016 - TRDOS 386 (TRDOS v2.0)
  4792                              <1> 	; 03/01/2016
  4793                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4794                              <1> 	; 07/07/2013 - 05/08/2013 (Retro UNIX 8086 v1)
  4795                              <1> 	;
  4796                              <1> 	; 'seektell' puts the arguments from sysseek and systell
  4797                              <1> 	; call in u.base and u.count. It then gets the i-number of
  4798                              <1> 	; the file from the file descriptor in u.r0 and by calling
  4799                              <1> 	; getf. The i-node is brought into core and then u.count
  4800                              <1> 	; is checked to see it is a 0, 1, or 2.
  4801                              <1> 	; If it is 0 - u.count stays the same
  4802                              <1> 	;          1 - u.count = offset (u.fofp)
  4803                              <1> 	;	   2 - u.count = i.size (size of file)
  4804                              <1> 	; 	 		
  4805                              <1> 	; !! Retro UNIX 8086 v1 modification:
  4806                              <1> 	;	Argument 1, file descriptor is in BX;
  4807                              <1> 	;	Argument 2, offset is in CX;
  4808                              <1> 	;	Argument 3, ptrname/switch is in DX register.	
  4809                              <1> 	;
  4810                              <1> 	; ((Return -> eax = base for offset (position= base+offset))
  4811                              <1> 	;
  4812 0000E3CB 890D[84030300]      <1> 	mov 	[u.base], ecx ; offset
  4813                              <1> seektell0:
  4814 0000E3D1 8915[88030300]      <1> 	mov 	[u.count], edx
  4815                              <1> 	; EBX = file descriptor (file number)
  4816 0000E3D7 E8F3FEFFFF          <1> 	call	getf1
  4817                              <1> 	; EAX = First cluster of the file
  4818                              <1> 	; EBX = File number (Open file number)
  4819                              <1> 	; [u.fofp] = Pointer to File pointer
  4820                              <1> 	; [i.size] = File size
  4821                              <1> 
  4822 0000E3DC 09C0                <1> 	or	eax, eax
  4823 0000E3DE 7514                <1> 	jnz	short seektell1
  4824                              <1> 
  4825 0000E3E0 B80A000000          <1> 	mov	eax, ERR_FILE_NOT_OPEN
  4826 0000E3E5 A3[64030300]        <1> 	mov	[u.r0], eax 
  4827 0000E3EA A3[C8030300]        <1> 	mov	dword [u.error], eax ; 'file not open !'
  4828 0000E3EF E986EBFFFF          <1> 	jmp	error
  4829                              <1> 
  4830                              <1> seektell1:
  4831 0000E3F4 8B1D[74030300]      <1>         mov     ebx, [u.fofp]
  4832 0000E3FA 803D[88030300]01    <1> 	cmp	byte [u.count], 1
  4833 0000E401 7705                <1> 	ja	short seektell2
  4834 0000E403 7409                <1> 	je	short seektell3
  4835 0000E405 31C0                <1> 	xor	eax, eax
  4836 0000E407 C3                  <1> 	retn
  4837                              <1> 
  4838                              <1> seektell2:
  4839 0000E408 A1[55040300]        <1>         mov   	eax, [i.size]
  4840 0000E40D C3                  <1> 	retn
  4841                              <1> 
  4842                              <1> seektell3:
  4843 0000E40E 8B03                <1> 	mov	eax, [ebx]
  4844 0000E410 C3                  <1> 	retn
  4845                              <1> 
  4846                              <1> sysintr: ; / set interrupt handling
  4847                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4848                              <1> 	; 07/07/2013 (Retro UNIX 8086 v1)
  4849                              <1> 	;
  4850                              <1> 	; 'sysintr' sets the interrupt handling value. It puts
  4851                              <1> 	; argument of its call in u.intr then branches into 'sysquit'
  4852                              <1> 	; routine. u.tty is checked if to see if a control tty exists.
  4853                              <1> 	; If one does the interrupt character in the tty buffer is
  4854                              <1> 	; cleared and 'sysret'is called. If one does not exits
  4855                              <1> 	; 'sysret' is just called.	
  4856                              <1> 	;
  4857                              <1> 	; Calling sequence:
  4858                              <1> 	;	sysintr; arg
  4859                              <1> 	; Argument:
  4860                              <1> 	;	arg - if 0, interrupts (ASCII DELETE) are ignored.
  4861                              <1> 	;	    - if 1, intterupts cause their normal result
  4862                              <1> 	;		 i.e force an exit.
  4863                              <1> 	;	    - if arg is a location within the program,
  4864                              <1> 	;		control is passed to that location when
  4865                              <1> 	;		an interrupt occurs.	
  4866                              <1> 	; Inputs: -
  4867                              <1> 	; Outputs: -
  4868                              <1> 	; ...............................................................
  4869                              <1> 	;	
  4870                              <1> 	; Retro UNIX 8086 v1 modification: 
  4871                              <1> 	;       'sysintr' system call sets u.intr to value of BX
  4872                              <1> 	;	then branches into sysquit.
  4873                              <1> 	;
  4874 0000E411 66891D[AA030300]    <1> 	mov	[u.intr], bx
  4875                              <1> 		; jsr r0,arg; u.intr / put the argument in u.intr
  4876                              <1> 		; br 1f / go into quit routine
  4877 0000E418 E97DEBFFFF          <1> 	jmp	sysret
  4878                              <1> 
  4879                              <1> sysquit:
  4880                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4881                              <1> 	; 07/07/2013 (Retro UNIX 8086 v1)
  4882                              <1> 	;
  4883                              <1> 	; 'sysquit' turns off the quit signal. it puts the argument of
  4884                              <1> 	; the call in u.quit. u.tty is checked if to see if a control 
  4885                              <1> 	; tty exists. If one does the interrupt character in the tty
  4886                              <1> 	; buffer is cleared and 'sysret'is called. If one does not exits
  4887                              <1> 	; 'sysret' is just called.	
  4888                              <1> 	;
  4889                              <1> 	; Calling sequence:
  4890                              <1> 	;	sysquit; arg
  4891                              <1> 	; Argument:
  4892                              <1> 	;	arg - if 0, this call diables quit signals from the
  4893                              <1> 	;		typewriter (ASCII FS)
  4894                              <1> 	;	    - if 1, quits are re-enabled and cause execution to
  4895                              <1> 	;		cease and a core image to be produced.
  4896                              <1> 	;		 i.e force an exit.
  4897                              <1> 	;	    - if arg is an addres in the program,
  4898                              <1> 	;		a quit causes control to sent to that
  4899                              <1> 	;		location.	
  4900                              <1> 	; Inputs: -
  4901                              <1> 	; Outputs: -
  4902                              <1> 	; ...............................................................
  4903                              <1> 	;	
  4904                              <1> 	; Retro UNIX 8086 v1 modification: 
  4905                              <1> 	;       'sysquit' system call sets u.quit to value of BX
  4906                              <1> 	;	then branches into 'sysret'.
  4907                              <1> 	;
  4908 0000E41D 66891D[AC030300]    <1> 	mov	[u.quit], bx
  4909 0000E424 E971EBFFFF          <1> 	jmp	sysret
  4910                              <1> 		; jsr r0,arg; u.quit / put argument in u.quit
  4911                              <1> 	;1:
  4912                              <1> 		; mov u.ttyp,r1 / move pointer to control tty buffer
  4913                              <1> 			      ; / to r1
  4914                              <1> 		; beq sysret4 / return to user
  4915                              <1> 		; clrb 6(r1) / clear the interrupt character 
  4916                              <1> 			   ; / in the tty buffer
  4917                              <1> 		; br sysret4 / return to user
  4918                              <1> 
  4919                              <1> anyi: 
  4920                              <1> 	; 06/10/2016 (TRDOS 386 = TRDOS v2.0)
  4921                              <1> 	; Major Modification!
  4922                              <1> 	; TRDOS 386 does not permit to delete a file while it is open 
  4923                              <1> 	; The role of 'anyi' procedure has beeen changed to ensure that.
  4924                              <1> 	; 	
  4925                              <1> 	; 22/06/2015 (Retro UNIX 386 v1 - Beginning)
  4926                              <1> 	; 25/04/2013 (Retro UNIX 8086 v1)
  4927                              <1> 	;
  4928                              <1> 	; 'anyi' is called if a file deleted while open.
  4929                              <1> 	; "anyi" checks to see if someone else has opened this file.
  4930                              <1> 	;
  4931                              <1> 	; INPUTS ->
  4932                              <1> 	;    r1 - contains an i-number
  4933                              <1> 	;    fsp - start of table containing open files
  4934                              <1> 	;
  4935                              <1> 	; OUTPUTS ->
  4936                              <1> 	;    "deleted" flag set in fsp entry of another occurrence of
  4937                              <1> 	;	   this file and r2 points 1st word of this fsp entry.
  4938                              <1> 	;    if file not found - bit in i-node map is cleared
  4939                              <1> 	;    			 (i-node is freed)
  4940                              <1> 	;               all blocks related to i-node are freed
  4941                              <1> 	;	        all flags in i-node are cleared
  4942                              <1> 	; ((AX = R1)) input
  4943                              <1> 	;
  4944                              <1> 	;    (Retro UNIX Prototype : 02/12/2012, UNIXCOPY.ASM)
  4945                              <1>         ;    ((Modified registers: eDX, eCX, eBX, eSI, eDI, eBP))  
  4946                              <1> 	;
  4947                              <1> 	; / r1 contains an i-number
  4948                              <1> 
  4949                              <1> 	; TRDOS 386 (06/10/2016)
  4950                              <1> 	; 
  4951                              <1> 	; INPUT:
  4952                              <1> 	;	EAX = First Cluster
  4953                              <1> 	;	 DL = Logical DOS Drive Number
  4954                              <1> 	;
  4955                              <1> 	; OUTPUT:
  4956                              <1> 	;	CF = 1 -> EBX = File Handle/Number/Index
  4957                              <1> 	;	CF = 0 -> EBX = 0
  4958                              <1> 	;
  4959                              <1> 	; Modified Registers: EBX
  4960                              <1> 
  4961 0000E429 31DB                <1> 	xor	ebx, ebx
  4962                              <1> anyi_0: 
  4963 0000E42B 80BB[A66E0100]00    <1> 	cmp	byte [ebx+OF_MODE], 0 ; 0 = empty entry
  4964 0000E432 770A                <1> 	ja	short anyi_2 ; 1 (r), 2 (w) or 3 (r&w)
  4965                              <1> anyi_1:
  4966 0000E434 FEC3                <1> 	inc	bl
  4967 0000E436 80FB0A              <1> 	cmp	bl, OPENFILES ; max. count of open files
  4968 0000E439 72F0                <1> 	jb	short anyi_0
  4969 0000E43B 31C0                <1> 	xor	eax, eax
  4970 0000E43D C3                  <1> 	retn 
  4971                              <1> anyi_2:
  4972 0000E43E 3A93[9C6E0100]      <1> 	cmp	dl, [ebx+OF_DRIVE]
  4973 0000E444 75EE                <1> 	jne	short anyi_1
  4974 0000E446 66C1E302            <1> 	shl	bx, 2 ; *4 (dword offset)
  4975 0000E44A 3B83[746E0100]      <1> 	cmp	eax, [ebx+OF_FCLUSTER]
  4976 0000E450 7406                <1> 	je	short anyi_3
  4977 0000E452 66C1EB02            <1> 	shr	bx, 2 ; /4 (byte offset)
  4978 0000E456 EBDC                <1> 	jmp	short anyi_1 	
  4979                              <1> anyi_3:
  4980 0000E458 66C1EB02            <1> 	shr	bx, 2 ; /4 (bytes offset) (index)
  4981 0000E45C F9                  <1> 	stc
  4982 0000E45D C3                  <1> 	retn
  4983                              <1> 
  4984                              <1> ; Retro UNIX 386 v1 Kernel (v0.2) - SYS9.INC
  4985                              <1> ; Last Modification: 09/12/2015
  4986                              <1> 
  4987                              <1> syssleep:
  4988                              <1> 	; 29/06/2015 - (Retro UNIX 386 v1)
  4989                              <1> 	; 11/06/2014 - (Retro UNIX 8086 v1)
  4990                              <1> 	;
  4991                              <1> 	; Retro UNIX 8086 v1 feature only
  4992                              <1> 	; (INPUT -> none)
  4993                              <1> 	;
  4994 0000E45E 0FB61D[B3030300]    <1> 	movzx	ebx, byte [u.uno] ; process number
  4995 0000E465 8AA3[7F000300]      <1> 	mov	ah, [ebx+p.ttyc-1] ; current/console tty
  4996 0000E46B E841190000          <1> 	call	sleep
  4997 0000E470 E925EBFFFF          <1> 	jmp	sysret
  4998                              <1> 
  4999                              <1> _vp_clr:
  5000                              <1> 	; Reset/Clear Video Page
  5001                              <1> 	;
  5002                              <1> 	; 30/06/2015 - (Retro UNIX 386 v1)
  5003                              <1> 	; 21/05/2013 - 30/10/2013(Retro UNIX 8086 v1) (U0.ASM)
  5004                              <1> 	;
  5005                              <1> 	; Retro UNIX 8086 v1 feature only !
  5006                              <1> 	;
  5007                              <1> 	; INPUTS -> 
  5008                              <1> 	;   BH = video page number	 
  5009                              <1> 	;
  5010                              <1> 	; OUTPUT ->
  5011                              <1> 	;   none
  5012                              <1> 	; ((Modified registers: eAX, BH, eCX, eDX, eSI, eDI))
  5013                              <1> 	;
  5014                              <1> 	; 04/12/2013
  5015 0000E475 28C0                <1> 	sub	al, al
  5016                              <1> 	; al = 0 (clear video page)
  5017                              <1> 	; bh = video page ; 13/05/2016
  5018 0000E477 B407                <1> 	mov	ah, 07h
  5019                              <1> 	; ah = 7 (attribute/color)
  5020 0000E479 6631C9              <1> 	xor 	cx, cx ; 0, left upper column (cl) & row (cl)
  5021 0000E47C 66BA4F18            <1> 	mov	dx, 184Fh ; right lower column & row (dl=24, dh=79)
  5022 0000E480 E88739FFFF          <1> 	call	_scroll_up
  5023                              <1> 	; bh = video page
  5024 0000E485 6631D2              <1> 	xor	dx, dx ; 0 (cursor position) 
  5025 0000E488 E9E63CFFFF          <1> 	jmp 	_set_cpos
  5026                              <1> 
  5027                              <1> sysmsg:
  5028                              <1> 	; 13/05/2016
  5029                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  5030                              <1> 	; 01/07/2015 - 11/11/2015 (Retro UNIX 386 v1)
  5031                              <1> 	; Print user-application message on user's console tty
  5032                              <1> 	;
  5033                              <1> 	; Input -> EBX = Message address
  5034                              <1> 	;	   ECX = Message length (max. 255)
  5035                              <1> 	;	   DL = Color (IBM PC Rombios color attributes)
  5036                              <1> 	;
  5037 0000E48D 81F9FF000000        <1> 	cmp	ecx, MAX_MSG_LEN ; 255
  5038 0000E493 0F8701EBFFFF        <1> 	ja	sysret ; nothing to do with big message size
  5039 0000E499 08C9                <1> 	or	cl, cl
  5040 0000E49B 0F84F9EAFFFF        <1> 	jz	sysret
  5041 0000E4A1 20D2                <1> 	and	dl, dl
  5042 0000E4A3 7502                <1> 	jnz	short sysmsg0
  5043 0000E4A5 B207                <1> 	mov	dl, 07h ; default color
  5044                              <1> 		; (black background, light gray character) 
  5045                              <1> sysmsg0:
  5046 0000E4A7 891D[84030300]      <1> 	mov	[u.base], ebx
  5047 0000E4AD 8815[AF5E0100]      <1> 	mov	[ccolor], dl ; color attributes
  5048 0000E4B3 89E5                <1> 	mov	ebp, esp
  5049 0000E4B5 31DB                <1> 	xor	ebx, ebx ; 0
  5050 0000E4B7 891D[8C030300]      <1> 	mov	[u.nread], ebx ; 0
  5051                              <1> 	;
  5052 0000E4BD 381D[C6030300]      <1> 	cmp	[u.kcall], bl ; 0
  5053 0000E4C3 7769                <1> 	ja	short sysmsgk ; Temporary (01/07/2015)
  5054                              <1> 	;
  5055 0000E4C5 890D[88030300]      <1> 	mov	[u.count], ecx
  5056 0000E4CB 41                  <1> 	inc	ecx ; + 00h ; ASCIIZ
  5057 0000E4CC 29CC                <1> 	sub	esp, ecx
  5058 0000E4CE 89E7                <1> 	mov	edi, esp
  5059 0000E4D0 89E6                <1> 	mov	esi, esp
  5060 0000E4D2 66891D[C4030300]    <1> 	mov	[u.pcount], bx ; reset page (phy. addr.) counter
  5061                              <1> 	; 11/11/2015
  5062 0000E4D9 8A25[94030300]      <1> 	mov 	ah, [u.ttyp] ; recent open tty
  5063                              <1> 	; 0 = none
  5064 0000E4DF FECC                <1> 	dec	ah
  5065 0000E4E1 790C                <1> 	jns	short sysmsg1 
  5066 0000E4E3 8A1D[B3030300]      <1> 	mov	bl, [u.uno] ; process number	
  5067 0000E4E9 8AA3[7F000300]      <1> 	mov	ah, [ebx+p.ttyc-1] ; user's (process's) console tty
  5068                              <1> sysmsg1:
  5069 0000E4EF 8825[96030300]      <1> 	mov	[u.ttyn], ah
  5070                              <1> sysmsg2:
  5071 0000E4F5 E808080000          <1> 	call	cpass
  5072 0000E4FA 7416                <1> 	jz	short sysmsg5
  5073 0000E4FC AA                  <1> 	stosb
  5074 0000E4FD 20C0                <1> 	and	al, al
  5075 0000E4FF 75F4                <1> 	jnz	short sysmsg2
  5076                              <1> sysmsg3:
  5077 0000E501 80FC07              <1> 	cmp	ah, 7 ; tty number
  5078 0000E504 7711                <1> 	ja	short sysmsg6 ; serial port
  5079 0000E506 E83E000000          <1> 	call	print_cmsg
  5080                              <1> sysmsg4:
  5081 0000E50B 89EC                <1> 	mov	esp, ebp	
  5082 0000E50D E988EAFFFF          <1> 	jmp	sysret
  5083                              <1> sysmsg5:
  5084 0000E512 C60700              <1> 	mov	byte [edi], 0
  5085 0000E515 EBEA                <1> 	jmp	short sysmsg3
  5086                              <1> sysmsg6:
  5087 0000E517 8A06                <1> 	mov	al, [esi]
  5088 0000E519 E891180000          <1> 	call	sndc
  5089 0000E51E 72EB                <1> 	jc	short sysmsg4
  5090 0000E520 803E00              <1> 	cmp	byte [esi], 0  ; 0 is stop character
  5091 0000E523 76E6                <1> 	jna	short sysmsg4
  5092 0000E525 46                  <1> 	inc 	esi
  5093 0000E526 8A25[96030300]      <1> 	mov	ah, [u.ttyn]
  5094 0000E52C EBE9                <1> 	jmp	short sysmsg6
  5095                              <1> 
  5096                              <1> sysmsgk: ; Temporary (01/07/2015)
  5097                              <1> 	; The message has been sent by Kernel (ASCIIZ string)
  5098                              <1> 	; (ECX -character count- will not be considered)
  5099 0000E52E 8B35[84030300]      <1> 	mov	esi, [u.base]
  5100 0000E534 8A25[AE5E0100]      <1> 	mov	ah, [ptty] ; present/current screen (video page)
  5101 0000E53A 8825[96030300]      <1> 	mov	[u.ttyn], ah
  5102 0000E540 C605[C6030300]00    <1> 	mov	byte [u.kcall], 0
  5103 0000E547 EBB8                <1> 	jmp	short sysmsg3
  5104                              <1> 	
  5105                              <1> print_cmsg: 
  5106                              <1> 	; 18/11/2017
  5107                              <1> 	; 13/05/2016 - TRDOS 386 (TRDOS v2.0)
  5108                              <1> 	; 01/07/2015 (Retro UNIX 386 v1)
  5109                              <1> 	;
  5110                              <1> 	; print message (on user's console tty) 
  5111                              <1> 	;	with requested color
  5112                              <1> 	;
  5113                              <1> 	; INPUTS:
  5114                              <1> 	;	esi = message address
  5115                              <1> 	;	[u.ttyn] = tty number (0 to 7)
  5116                              <1> 	;	[ccolor] = color attributes (IBM PC BIOS colors)
  5117                              <1> 	
  5118                              <1> 	;mov	bh, ah
  5119 0000E549 8A3D[96030300]      <1> 	mov	bh, [u.ttyn]
  5120                              <1> 	;mov	bl, [ccolor] ; *
  5121                              <1> pcmsg1:
  5122 0000E54F AC                  <1> 	lodsb
  5123 0000E550 20C0                <1> 	and 	al, al  ; 0
  5124 0000E552 740F                <1> 	jz 	short pcmsg2
  5125 0000E554 56                  <1> 	push 	esi
  5126 0000E555 8A1D[AF5E0100]      <1> 	mov	bl, [ccolor]  ; * (video.s 'u11'&'beep' change BL)
  5127                              <1> 	;mov	bh, [u.ttyn]
  5128 0000E55B E8753BFFFF          <1> 	call 	_write_tty 
  5129 0000E560 5E                  <1> 	pop	esi
  5130 0000E561 EBEC                <1> 	jmp	short pcmsg1
  5131                              <1> pcmsg2:
  5132 0000E563 C3                  <1> 	retn
  5133                              <1> 
  5134                              <1> sysgeterr:
  5135                              <1> 	; 09/12/2015
  5136                              <1> 	; 21/09/2015 - (Retro UNIX 386 v1 feature only!)
  5137                              <1> 	; Get last error number or page fault count
  5138                              <1> 	; (for debugging)
  5139                              <1> 	;
  5140                              <1> 	; Input -> EBX = return type
  5141                              <1> 	;	   0 = last error code (which is in 'u.error')	
  5142                              <1> 	;	   FFFFFFFFh = page fault count for running process
  5143                              <1> 	;	   FFFFFFFEh = total page fault count
  5144                              <1> 	;	   1 .. FFFFFFFDh = undefined 
  5145                              <1> 	;
  5146                              <1> 	; Output -> EAX = last error number or page fault count
  5147                              <1> 	;	   (depending on EBX input)
  5148                              <1> 	; 	
  5149 0000E564 21DB                <1> 	and 	ebx, ebx
  5150 0000E566 750B                <1> 	jnz	short glerr_2
  5151                              <1> glerr_0:
  5152 0000E568 A1[C8030300]        <1> 	mov	eax, [u.error]
  5153                              <1> glerr_1:
  5154 0000E56D A3[64030300]        <1> 	mov	[u.r0], eax
  5155 0000E572 C3                  <1>  	retn
  5156                              <1> glerr_2:
  5157 0000E573 43                  <1> 	inc	ebx ; FFFFFFFFh -> 0, FFFFFFFEh -> FFFFFFFFh
  5158 0000E574 74FD                <1> 	jz	short glerr_2 ; page fault count for process
  5159 0000E576 43                  <1> 	inc	ebx ; FFFFFFFFh -> 0	
  5160 0000E577 75EF                <1> 	jnz	short glerr_0
  5161 0000E579 A1[80050300]        <1> 	mov	eax, [PF_Count] ; total page fault count
  5162 0000E57E EBED                <1>         jmp     short glerr_1
  5163                              <1> glerr_3:
  5164 0000E580 A1[CC030300]        <1> 	mov 	eax, [u.pfcount]
  5165 0000E585 EBE6                <1> 	jmp	short glerr_1
  5166                              <1> 
  5167                              <1> load_and_run_file:
  5168                              <1> 	; 18/11/2017
  5169                              <1> 	; 22/01/2017
  5170                              <1> 	; 04/01/2017, 07/01/2017
  5171                              <1> 	; 24/10/2016
  5172                              <1> 	; 24/04/2016, 02/05/2016, 03/05/2016, 06/05/2016
  5173                              <1> 	; 23/04/2016 (TRDOS 386 = TRDOS v2.0)
  5174                              <1> 	; 23/10/2015 (Retro UNIX 386 v1, 'sysexec')
  5175                              <1> 	; 23/06/2015 (Retro UNIX 386 v1 - Beginning)
  5176                              <1> 	; 03/06/2013 - 06/12/2013 (Retro UNIX 8086 v1)
  5177                              <1> 	; EAX = First Cluster number
  5178                              <1> 	; EDX = File Size
  5179                              <1> 	; ESI = Argument list address
  5180                              <1> 	; [argc] = argument count
  5181                              <1> 	; [u.nread] = argument list length
  5182                              <1> 	; [esp] = return address to the caller (*)
  5183                              <1> 	;
  5184 0000E587 8935[4C040300]      <1> 	mov	[argv], esi
  5185 0000E58D 8915[55040300]      <1> 	mov	[i.size], edx
  5186 0000E593 A3[51040300]        <1> 	mov	[ii], eax
  5187                              <1> 
  5188                              <1> 	;sti	; 07/01/2017
  5189                              <1> 	;mov	eax, [k_page_dir]
  5190                              <1> 	;mov	[u.pgdir], eax
  5191 0000E598 31C0                <1> 	xor 	eax, eax ; clc ; *** ; 04/01/2017
  5192                              <1> 	;mov	[u.r0], eax ; 0 ; 07/01/2017
  5193                              <1> 
  5194                              <1> 	; 06/05/2016
  5195                              <1> 	; Set 'sysexit' return order to MainProg
  5196                              <1> 	;
  5197 0000E59A 58                  <1> 	pop	eax ; * 'loc_load_and_run_file_8:' address
  5198                              <1> 	;; 22/01/2017
  5199                              <1> 	;;cli ; 07/01/2017
  5200 0000E59B 8B25[1C5E0100]      <1> 	mov	esp, [tss.esp0]
  5201                              <1> 	;
  5202                              <1> 	; 'loc_load_run_file_8' address has 
  5203                              <1> 	; 'jmp loc_file_rw_restore_retn' instruction
  5204                              <1> 	; 'loc_file_rw_restore_retn:' will return to
  5205                              <1> 	; [mainprog_return_addr] 
  5206                              <1> 	; just after 'call command_interpreter'
  5207                              <1> 	;
  5208 0000E5A1 68[E36B0000]        <1> 	push	_end_of_mainprog ; we must not return to here !
  5209 0000E5A6 FF35[006B0100]      <1> 	push	dword [mainprog_return_addr]
  5210 0000E5AC 89E5                <1> 	mov	ebp, esp ; **
  5211                              <1> 	;	
  5212 0000E5AE 9C                  <1> 	pushfd  ; EFLAGS      ; IRETD ; ***
  5213 0000E5AF 6A08                <1> 	push	KCODE ; cs    ; IRETD
  5214 0000E5B1 50                  <1> 	push	eax ; * (eip) ; IRETD
  5215 0000E5B2 8925[5C030300]      <1> 	mov	[u.sp], esp
  5216                              <1> 	;mov	byte [u.quant], time_count
  5217 0000E5B8 1E                  <1> 	push	ds
  5218 0000E5B9 06                  <1> 	push	es
  5219 0000E5BA 0FA0                <1> 	push	fs
  5220 0000E5BC 0FA8                <1> 	push	gs	
  5221                              <1> 	;mov	eax, [u.r0]
  5222 0000E5BE 29C0                <1> 	sub	eax, eax
  5223 0000E5C0 60                  <1> 	pushad
  5224 0000E5C1 68[9ACF0000]        <1> 	push	sysret
  5225                              <1> 	;push	sysrel1 ; 07/01/2017
  5226 0000E5C6 8925[60030300]      <1> 	mov	[u.usp], esp
  5227                              <1> 	;
  5228 0000E5CC E845060000          <1> 	call	wswap ; Save MainProg (process 1) 'u' structure
  5229                              <1> 		      ; and registers for return (from program)	
  5230 0000E5D1 89EC                <1> 	mov	esp, ebp ; **
  5231                              <1> 	;;22/01/2017
  5232                              <1> 	;;sti ; 07/01/2017
  5233 0000E5D3 50                  <1> 	push	eax  ; * 'loc_load_and_run_file_8:' address
  5234                              <1> 	;
  5235                              <1> 	;;; 02/05/2016
  5236                              <1> 	;;; Create a new process (parent: MainProg)	
  5237 0000E5D4 31F6                <1> 	xor 	esi, esi
  5238                              <1> cnpm_1: ; search p.stat table for unused process number
  5239 0000E5D6 46                  <1> 	inc	esi
  5240 0000E5D7 80BE[AF000300]00    <1> 	cmp	byte [esi+p.stat-1], 0 ; SFREE
  5241                              <1> 				; is process active, unused, dead
  5242 0000E5DE 760B                <1> 	jna	short cnpm_2	; it's unused so branch
  5243 0000E5E0 6683FE10            <1> 	cmp	si, nproc 	; all processes checked
  5244 0000E5E4 72F0                <1> 	jb	short cnpm_1    ; no, branch back
  5245 0000E5E6 E96E86FFFF          <1> 	jmp	panic 
  5246                              <1> cnpm_2:
  5247 0000E5EB A1[B8030300]        <1> 	mov	eax, [u.pgdir] ; page directory of MainProg
  5248 0000E5F0 A3[BC030300]        <1> 	mov	[u.ppgdir], eax ; parent's page directory
  5249 0000E5F5 E8EB6CFFFF          <1> 	call	allocate_page
  5250 0000E5FA 0F825986FFFF        <1> 	jc	panic
  5251                              <1> 	; EAX = UPAGE (user structure page) address
  5252 0000E600 A3[B4030300]        <1> 	mov	[u.upage], eax ; memory page for 'user' struct (child)
  5253 0000E605 89F7                <1> 	mov	edi, esi
  5254 0000E607 66C1E702            <1> 	shl	di, 2
  5255 0000E60B 8987[BC000300]      <1> 	mov	[edi+p.upage-4], eax ; memory page for 'user' struct
  5256 0000E611 E8496DFFFF          <1> 	call	clear_page ; 03/05/2016
  5257                              <1> 	;movzx	eax, byte [p.ttyc] ; console tty (for MainProg)
  5258 0000E616 6629C0              <1> 	sub	ax, ax ; 0
  5259 0000E619 668986[7F000300]    <1> 	mov     [esi+p.ttyc-1], ax ; al - set child's console tty
  5260                              <1> 				   ; ah - reset child's wait channel	
  5261 0000E620 89F0                <1> 	mov	eax, esi
  5262 0000E622 A2[B3030300]        <1> 	mov	[u.uno], al ; child process number
  5263 0000E627 FE86[AF000300]      <1>         inc     byte [esi+p.stat-1] ; 1, SRUN
  5264 0000E62D 66D1E6              <1> 	shl	si, 1 ; multiply si by 2 to get index into p.pid table
  5265 0000E630 66FF05[4E030300]    <1> 	inc	word [mpid] ; increment m.pid; get a new process name
  5266 0000E637 66A1[4E030300]      <1> 	mov	ax, [mpid]
  5267 0000E63D 668986[1E000300]    <1> 	mov	[esi+p.pid-2], ax ; put new process name 
  5268                              <1> 				  ; in child process' name slot
  5269                              <1> 	;mov	ax, [p.pid]  ; get process name of MainProg
  5270 0000E644 66B80100            <1> 	mov	ax, 1
  5271 0000E648 668986[3E000300]    <1> 	mov	[esi+p.ppid-2], ax ; put parent process name 
  5272                              <1> 			           ; in parent process slot for child
  5273 0000E64F 6648                <1> 	dec	ax ; 0
  5274 0000E651 66A3[94030300]      <1> 	mov 	[u.ttyp], ax ; 0
  5275                              <1> 	;;;
  5276 0000E657 A1[51040300]        <1> 	mov 	eax,  [ii]
  5277                              <1> 	; Retro UNIX 386 v1, 'sysexec' (u2.s)
  5278 0000E65C E84C170000          <1> 	call	iopen
  5279                              <1> 	; 06/06/2016
  5280 0000E661 C605[A9030300]01    <1> 	mov	byte [u.pri], 1 ; normal priority
  5281                              <1> 	;
  5282 0000E668 EB16                <1> 	jmp	short sysexec_7 ; 02/05/2016
  5283                              <1> 
  5284                              <1> sysexec_6:
  5285                              <1> 	; 19/11/2017
  5286                              <1> 	; 18/11/2017
  5287                              <1> 	; 14/11/2017
  5288                              <1> 	; 13/11/2017
  5289 0000E66A 8925[4C040300]      <1> 	mov	[argv], esp ; *!* ; start address of argument list 
  5290                              <1> 
  5291                              <1> 	; 04/01/2017
  5292                              <1> 	; 24/10/2016
  5293                              <1> 	;;02/05/2016
  5294                              <1> 	; 23/04/2016 (TRDOS 386)
  5295                              <1> 	; 18/10/2015 ('sysexec_6')
  5296                              <1> 	; 23/06/2015
  5297 0000E670 A1[B8030300]        <1> 	mov	eax, [u.pgdir] ; physical address of page directory
  5298                              <1> 	;cmp 	eax, [k_page_dir] ; TRDOS MainProg ? 
  5299                              <1> 	;je	short sysexec_7
  5300                              <1> 	; 19/11/2017
  5301 0000E675 8B1D[BC030300]      <1> 	mov	ebx, [u.ppgdir] ; phy addr of the parent's page dir
  5302 0000E67B E89E6DFFFF          <1> 	call	deallocate_page_dir
  5303                              <1> sysexec_7:
  5304 0000E680 E8CE6CFFFF          <1> 	call	make_page_dir
  5305 0000E685 0F82CE85FFFF        <1> 	jc	panic  ; allocation error 
  5306                              <1> 		       ; after a deallocation would be nonsence !?
  5307                              <1> 	; 24/07/2015
  5308                              <1> 	; map kernel pages (1st 4MB) to PDE 0
  5309                              <1> 	;     of the user's page directory
  5310                              <1> 	;     (It is needed for interrupts!)
  5311                              <1> 	; 18/10/2015
  5312 0000E68B 8B15[805E0100]      <1> 	mov	edx, [k_page_dir] ; Kernel's page directory
  5313 0000E691 8B02                <1> 	mov	eax, [edx] ; physical address of
  5314                              <1> 			   ; kernel's first page table (1st 4 MB)
  5315                              <1> 			   ; (PDE 0 of kernel's page directory)
  5316 0000E693 8B15[B8030300]      <1> 	mov 	edx, [u.pgdir]
  5317 0000E699 8902                <1> 	mov	[edx], eax ; PDE 0 (1st 4MB)
  5318                              <1> 	;
  5319                              <1> 	; 20/07/2015
  5320 0000E69B BB00004000          <1> 	mov	ebx, CORE ; start address = 0 (virtual) + CORE
  5321                              <1> 	; 18/10/2015
  5322 0000E6A0 BE[3C040300]        <1> 	mov	esi, pcore ; physical start address
  5323                              <1> sysexec_8:	
  5324 0000E6A5 B907000000          <1> 	mov	ecx, PDE_A_USER + PDE_A_WRITE + PDE_A_PRESENT
  5325 0000E6AA E8C26CFFFF          <1> 	call	make_page_table
  5326 0000E6AF 0F82A485FFFF        <1> 	jc	panic
  5327                              <1> 	;mov	ecx, PTE_A_USER + PTE_A_WRITE + PTE_A_PRESENT
  5328 0000E6B5 E8C56CFFFF          <1> 	call	make_page ; make new page, clear and set the pte 
  5329 0000E6BA 0F829985FFFF        <1> 	jc	panic
  5330                              <1> 	;
  5331 0000E6C0 8906                <1> 	mov	[esi], eax ; 24/06/2015
  5332                              <1> 	; ebx = virtual address (24/07/2015)
  5333 0000E6C2 E85D72FFFF          <1> 	call 	add_to_swap_queue
  5334                              <1> 	; 18/10/2015
  5335 0000E6C7 81FE[40040300]      <1> 	cmp	esi, ecore ; user's stack (last) page ?
  5336 0000E6CD 740C                <1> 	je	short sysexec_9 ; yes
  5337 0000E6CF BE[40040300]        <1> 	mov	esi, ecore  ; physical address of the last page 
  5338                              <1> 	; 20/07/2015
  5339 0000E6D4 BB00F0FFFF          <1> 	mov	ebx, (ECORE - PAGE_SIZE) + CORE
  5340                              <1> 	; ebx = virtual end address + segment base address - 4K
  5341 0000E6D9 EBCA                <1>         jmp     short sysexec_8
  5342                              <1> sysexec_9:
  5343                              <1> 	; 19/11/2017 
  5344                              <1> 	; 24/04/2016 (TRDOS 386 = TRDOS v2.0)
  5345                              <1> 	; 25/06/2015, 26/08/2015, 18/10/2015
  5346                              <1> 	; move arguments from kernel stack to [ecore]
  5347                              <1> 	; (argument list/line will be copied from kernel stack
  5348                              <1> 	; frame to the last (stack) page of user's core memory)
  5349                              <1> 	; 18/10/2015
  5350 0000E6DB 8B3D[40040300]      <1> 	mov	edi, [ecore]
  5351 0000E6E1 81C700100000        <1> 	add	edi, PAGE_SIZE
  5352                              <1> 	; 19/11/2017
  5353 0000E6E7 83EF04              <1> 	sub	edi, 4
  5354 0000E6EA C70700000000        <1> 	mov	dword [edi], 0 
  5355 0000E6F0 89FB                <1> 	mov	ebx, edi
  5356                              <1> 	;
  5357 0000E6F2 0FB705[4A040300]    <1> 	movzx	eax, word [argc]
  5358 0000E6F9 09C0                <1> 	or	eax, eax
  5359 0000E6FB 7445                <1> 	jz	short sysexec_13 ; 19/11/2017
  5360                              <1> 	;jnz	short sysexec_10
  5361                              <1> 	;mov 	ebx, edi
  5362                              <1> 	;sub	ebx, 4 
  5363                              <1> 	;mov	[ebx], eax ; 0
  5364                              <1> 	;jmp 	short sysexec_13
  5365                              <1> sysexec_10:
  5366 0000E6FD 8B0D[8C030300]      <1> 	mov	ecx, [u.nread]
  5367                              <1> 	; 13/11/2017
  5368                              <1> 	;mov	esi, TextBuffer ; 'load_and_execute_file'
  5369                              <1> 	;mov	esi, esp  	; 'sysexec'
  5370 0000E703 8B35[4C040300]      <1> 	mov	esi, [argv] ; 24/04/2016 (TRDOS 386  = TRDOS v2.0)
  5371                              <1> 	;sub	edi, ecx ; page end address - argument list length
  5372 0000E709 29CB                <1> 	sub	ebx, ecx ; 19/11/2017
  5373 0000E70B 89C2                <1> 	mov	edx, eax
  5374 0000E70D FEC2                <1> 	inc	dl ; argument count + 1 for argc value  
  5375 0000E70F C0E202              <1> 	shl 	dl, 2  ; 4 * (argument count + 1)
  5376                              <1> 	;mov	ebx, edi
  5377 0000E712 89DF                <1> 	mov	edi, ebx ; 19//11/2017
  5378 0000E714 80E3FC              <1> 	and	bl, 0FCh ; 32 bit (dword) alignment
  5379 0000E717 29D3                <1> 	sub 	ebx, edx
  5380 0000E719 89FA                <1> 	mov	edx, edi
  5381 0000E71B F3A4                <1> 	rep	movsb
  5382 0000E71D 89D6                <1> 	mov 	esi, edx
  5383 0000E71F 89DF                <1> 	mov 	edi, ebx
  5384 0000E721 BA00F0BFFF          <1> 	mov	edx, ECORE - PAGE_SIZE ; virtual addr. of the last page
  5385 0000E726 2B15[40040300]      <1> 	sub 	edx, [ecore] ; difference (virtual - physical) 
  5386 0000E72C AB                  <1> 	stosd	; eax = argument count	
  5387                              <1> sysexec_11:
  5388 0000E72D 89F0                <1> 	mov	eax, esi
  5389 0000E72F 01D0                <1> 	add	eax, edx
  5390 0000E731 AB                  <1> 	stosd  ; eax = virtual address
  5391                              <1> 	;dec	byte [argc]
  5392 0000E732 66FF0D[4A040300]    <1> 	dec	word [argc] ; 14/11/2017
  5393 0000E739 7407                <1> 	jz	short sysexec_13
  5394                              <1> sysexec_12:
  5395 0000E73B AC                  <1> 	lodsb
  5396 0000E73C 20C0                <1> 	and	al, al
  5397 0000E73E 75FB                <1> 	jnz	short sysexec_12
  5398 0000E740 EBEB                <1> 	jmp	short sysexec_11
  5399                              <1> sysexec_13:
  5400                              <1> 	; 24/10/2016
  5401                              <1> 	; 24/04/2016 - TRDOS 386 (TRDOS v2.0)
  5402                              <1> 	; 23/06/2015 - 19/10/2015 (Retro UNIX 386 v1, 'sysexec_13')
  5403                              <1> 	;
  5404                              <1> 	; moving arguments to [ecore] is OK here..
  5405                              <1> 	;
  5406                              <1> 	; ebx = beginning addres of argument list pointers
  5407                              <1> 		;	in user's stack
  5408 0000E742 2B1D[40040300]      <1> 	sub 	ebx, [ecore]
  5409 0000E748 81C300F0BFFF        <1> 	add     ebx, (ECORE - PAGE_SIZE)
  5410                              <1> 			; end of core - 4096 (last page)
  5411                              <1> 			; (virtual address)
  5412 0000E74E 891D[4C040300]      <1> 	mov	[argv], ebx
  5413 0000E754 891D[90030300]      <1> 	mov	[u.break], ebx ; available user memory
  5414                              <1> 	;
  5415 0000E75A 29C0                <1> 	sub	eax, eax
  5416 0000E75C C705[88030300]2000- <1> 	mov	dword [u.count], 32 ; Executable file header size
  5416 0000E764 0000                <1>
  5417 0000E766 C705[74030300]-     <1> 	mov	dword [u.fofp], u.off
  5417 0000E76C [80030300]          <1>
  5418 0000E770 A3[80030300]        <1> 	mov	[u.off], eax ; 0
  5419 0000E775 A3[84030300]        <1> 	mov	[u.base], eax ; 0, start of user's core (virtual)
  5420                              <1> 	; 24/10/2016
  5421 0000E77A A0[465F0100]        <1> 	mov	al, [Current_Drv]
  5422 0000E77F A2[46030300]        <1> 	mov	[cdev], al
  5423                              <1> 	;
  5424 0000E784 A1[51040300]        <1> 	mov	eax, [ii] ; Fist Cluster of the Program (PRG) file
  5425                              <1> 	; EAX = First cluster of the executable file
  5426 0000E789 E80A010000          <1> 	call	readi
  5427                              <1> 
  5428 0000E78E 8B0D[90030300]      <1> 	mov	ecx, [u.break] ; top of user's stack (physical addr.)
  5429 0000E794 890D[88030300]      <1> 	mov	[u.count], ecx ; save for overrun check
  5430                              <1> 	;
  5431 0000E79A 8B0D[8C030300]      <1> 	mov	ecx, [u.nread]
  5432 0000E7A0 890D[90030300]      <1> 	mov	[u.break], ecx ; virtual address (offset from start)
  5433 0000E7A6 80F920              <1> 	cmp	cl, 32
  5434 0000E7A9 7540                <1>         jne     short sysexec_15
  5435                              <1> 	;:
  5436                              <1> 	; Retro UNIX 386 v1 (32 bit) executable file header format
  5437 0000E7AB 8B35[3C040300]      <1> 	mov	esi, [pcore] ; start address of user's core memory 
  5438                              <1> 		             ; (phys. start addr. of the exec. file)
  5439 0000E7B1 AD                  <1> 	lodsd
  5440 0000E7B2 663DEB1E            <1> 	cmp	ax, 1EEBh ; EBH, 1Eh -> jump to +32
  5441 0000E7B6 7533                <1> 	jne	short sysexec_15
  5442 0000E7B8 AD                  <1> 	lodsd
  5443 0000E7B9 89C1                <1> 	mov	ecx, eax ; text (code) section size
  5444 0000E7BB AD                  <1> 	lodsd
  5445 0000E7BC 01C1                <1> 	add	ecx, eax ; + data section size (initialized data)
  5446 0000E7BE 89CB                <1> 	mov	ebx, ecx
  5447 0000E7C0 AD                  <1> 	lodsd	
  5448 0000E7C1 01C3                <1> 	add	ebx, eax ; + bss section size (for overrun checking)
  5449 0000E7C3 3B1D[88030300]      <1> 	cmp	ebx, [u.count]
  5450 0000E7C9 7711                <1> 	ja	short sysexec_14  ; program overruns stack !
  5451                              <1> 	;
  5452                              <1> 	; add bss section size to [u.break]
  5453 0000E7CB 0105[90030300]      <1> 	add 	[u.break], eax
  5454                              <1> 	;
  5455 0000E7D1 83E920              <1> 	sub	ecx, 32  ; header size (already loaded)
  5456                              <1> 	;cmp	ecx, [u.count]
  5457                              <1> 	;jnb	short sysexec_16
  5458 0000E7D4 890D[88030300]      <1> 	mov	[u.count], ecx ; required read count
  5459 0000E7DA EB29                <1> 	jmp	short sysexec_16
  5460                              <1> sysexec_14:
  5461                              <1> 	; insufficient (out of) memory
  5462 0000E7DC C705[C8030300]0400- <1> 	mov	dword [u.error], ERR_MINOR_IM ; 1
  5462 0000E7E4 0000                <1>
  5463 0000E7E6 E98FE7FFFF          <1> 	jmp	error
  5464                              <1> sysexec_15:
  5465 0000E7EB 8B15[55040300]      <1>         mov	edx, [i.size] ; file size
  5466 0000E7F1 29CA                <1> 	sub	edx, ecx ; file size - loaded bytes
  5467 0000E7F3 7626                <1> 	jna	short sysexec_17 ; no need to next read
  5468 0000E7F5 01D1                <1> 	add	ecx, edx ; [i.size]
  5469 0000E7F7 3B0D[88030300]      <1> 	cmp	ecx, [u.count] ; overrun check (!)
  5470 0000E7FD 77DD                <1> 	ja	short sysexec_14
  5471 0000E7FF 8915[88030300]      <1> 	mov	[u.count], edx
  5472                              <1> sysexec_16:
  5473 0000E805 A1[51040300]        <1> 	mov	eax, [ii] ; first cluster
  5474 0000E80A E889000000          <1> 	call	readi
  5475 0000E80F 8B0D[8C030300]      <1> 	mov	ecx, [u.nread]
  5476 0000E815 010D[90030300]      <1> 	add	[u.break], ecx
  5477                              <1> sysexec_17:
  5478 0000E81B A1[51040300]        <1> 	mov	eax, [ii] ; first cluster
  5479 0000E820 E889150000          <1> 	call	iclose
  5480 0000E825 31C0                <1> 	xor     eax, eax
  5481 0000E827 FEC0                <1> 	inc	al
  5482 0000E829 66A3[AA030300]      <1> 	mov	[u.intr], ax ; 1 (interrupt/time-out is enabled)
  5483 0000E82F 66A3[AC030300]      <1> 	mov	[u.quit], ax ; 1 ('crtl+brk' signal is enabled) 
  5484 0000E835 833D[BC030300]00    <1>         cmp	dword [u.ppgdir], 0  ; is the caller MainProg (kernel) ?
  5485 0000E83C 770C                <1> 	ja	short sysexec_18 ; no, the caller is user process
  5486                              <1> 	; If the caller is kernel (MainProg), 'sysexec' will come here
  5487 0000E83E 8B15[805E0100]      <1> 	mov	edx, [k_page_dir] ; kernel's page directory
  5488 0000E844 8915[BC030300]      <1> 	mov	[u.ppgdir], edx ; next time 'sysexec' must not come here 
  5489                              <1> sysexec_18:
  5490                              <1> 	; 02/05/2016
  5491                              <1> 	; 24/04/2016 (TRDOS 386 = TRDOS v2.0)
  5492                              <1> 	; 18/10/2015 (Retro UNIX 386 v1)
  5493                              <1> 	; 05/08/2015
  5494                              <1> 	; 29/07/2015
  5495                              <1> 
  5496                              <1> ;	; **** arguments list test start - 19/11/2017
  5497                              <1> ;	mov	ebp, [argv]
  5498                              <1> ;	sub	ebp, ECORE - 4096
  5499                              <1> ;	add	ebp, [ecore]
  5500                              <1> ;
  5501                              <1> ;	mov	ebx, [ebp]
  5502                              <1> ;	mov	[argc], bx
  5503                              <1> ;	add	ebp, 4
  5504                              <1> ;	mov	byte [ccolor], 1Fh
  5505                              <1> ;_zx0:
  5506                              <1> ;	cmp	word [argc], 0
  5507                              <1> ;	jna	short _zx2	
  5508                              <1> ;_zx1:
  5509                              <1> ;	push	ebp
  5510                              <1> ;	mov	esi, [ebp]
  5511                              <1> ;
  5512                              <1> ;	sub	esi, ECORE - 4096
  5513                              <1> ;	add	esi, [ecore]
  5514                              <1> ;
  5515                              <1> ;	call	print_cmsg
  5516                              <1> ;
  5517                              <1> ;	dec	word [argc]
  5518                              <1> ;	jz	short _zx2
  5519                              <1> ;
  5520                              <1> ;	mov	al, '.'
  5521                              <1> ;	mov	bl, 07h
  5522                              <1> ;	mov	bh, [u.ttyn]
  5523                              <1> ;	call 	_write_tty 
  5524                              <1> ;
  5525                              <1> ;	pop	ebp
  5526                              <1> ;	add	ebp, 4
  5527                              <1> ;	jmp	short _zx1			
  5528                              <1> ;_zx2:
  5529                              <1> ;	pop	ebp
  5530                              <1> ;	mov	byte [ccolor], 07h
  5531                              <1> ;	mov	eax, 1
  5532                              <1> ;	; **** arguments list test stop
  5533                              <1> ;	Test result is OK! (there is not a wrong thing) - 19/11/2017
  5534                              <1> 
  5535 0000E84A 8B2D[4C040300]      <1> 	mov	ebp, [argv] ; user's stack pointer must point to argument
  5536                              <1> 			    ; list pointers (argument count)
  5537 0000E850 FA                  <1> 	cli
  5538 0000E851 8B25[1C5E0100]      <1>         mov     esp, [tss.esp0] ; ring 0 (kernel) stack pointer
  5539                              <1> 	;mov   	esp, [u.sp] ; Restore Kernel stack
  5540                              <1> 			    ; for this process	 
  5541                              <1> 	;add	esp, 20 ; --> EIP, CS, EFLAGS, ESP, SS
  5542                              <1> 	;xor	eax, eax ; 0
  5543 0000E857 FEC8                <1> 	dec	al ; eax = 0
  5544                              <1> 	;mov	edx, UDATA
  5545                              <1> 	; 18/11/2017
  5546 0000E859 6A23                <1> 	push	UDATA ; user's stack segment
  5547                              <1> 	;push	edx
  5548 0000E85B 55                  <1> 	push	ebp ; user's stack pointer
  5549                              <1> 		    ; (points to number of arguments)
  5550                              <1> 	
  5551                              <1> 	; 04/01/2017
  5552                              <1> 	; MainProg comes here while [sysflg]= 0FFh
  5553                              <1> 	; (but sysexec comes here while [sysflg]= 0)
  5554 0000E85C C605[5B030300]00    <1> 	mov	byte [sysflg], 0 ; 04/01/2017
  5555                              <1> 				 ; (timer_int sysflg control)
  5556 0000E863 FB                  <1> 	sti
  5557 0000E864 9C                  <1> 	pushfd	; EFLAGS
  5558                              <1> 		; Set IF for enabling interrupts in user mode	
  5559                              <1> 	;or	dword [esp], 200h 
  5560                              <1> 	;
  5561                              <1> 	;mov	bx, UCODE
  5562                              <1> 	;push	bx ; user's code segment
  5563 0000E865 6A1B                <1> 	push	UCODE
  5564                              <1> 	;push	0
  5565 0000E867 50                  <1> 	push	eax ; EIP (=0) - start address -	
  5566 0000E868 8925[5C030300]      <1> 	mov	[u.sp], esp ; 29/07/2015
  5567                              <1> 	; 05/08/2015
  5568                              <1> 	; Remedy of a General Protection Fault during 'iretd' is here !
  5569                              <1> 	; ('push dx' would cause to general protection fault, 
  5570                              <1> 	; after 'pop ds' etc.)
  5571                              <1> 	;
  5572                              <1> 	;; push dx ; ds (UDATA)
  5573                              <1> 	;; push dx ; es (UDATA)
  5574                              <1> 	;; push dx ; fs (UDATA)
  5575                              <1> 	;; push dx ; gs (UDATA)
  5576                              <1> 	;
  5577                              <1> 	; This is a trick to prevent general protection fault
  5578                              <1> 	; during 'iretd' intruction at the end of 'sysrele' (in u1.s):
  5579 0000E86E 66BA2300            <1> 	mov	dx, UDATA ; 19/11/2017
  5580 0000E872 8EC2                <1> 	mov 	es, dx ; UDATA
  5581 0000E874 06                  <1> 	push 	es ; ds (UDATA)
  5582 0000E875 06                  <1> 	push 	es ; es (UDATA)
  5583 0000E876 06                  <1> 	push 	es ; fs (UDATA)
  5584 0000E877 06                  <1> 	push	es ; gs (UDATA)
  5585 0000E878 66BA1000            <1> 	mov	dx, KDATA
  5586 0000E87C 8EC2                <1> 	mov	es, dx
  5587                              <1> 	;
  5588                              <1> 	;; pushad simulation
  5589 0000E87E 89E5                <1> 	mov	ebp, esp ; esp before pushad
  5590 0000E880 50                  <1> 	push	eax ; eax (0)
  5591 0000E881 50                  <1> 	push	eax ; ecx (0)
  5592 0000E882 50                  <1> 	push	eax ; edx (0)
  5593 0000E883 50                  <1> 	push	eax ; ebx (0)
  5594 0000E884 55                  <1> 	push	ebp ; esp before pushad
  5595 0000E885 50                  <1> 	push	eax ; ebp (0)
  5596 0000E886 50                  <1> 	push	eax ; esi (0)		
  5597 0000E887 50                  <1> 	push	eax ; edi (0)	
  5598                              <1> 	;
  5599 0000E888 A3[64030300]        <1> 	mov	[u.r0], eax ; eax = 0
  5600 0000E88D 8925[60030300]      <1> 	mov	[u.usp], esp
  5601                              <1> 
  5602                              <1> 	; 14/11/2017
  5603 0000E893 E904E7FFFF          <1> 	jmp	sysret0
  5604                              <1> 
  5605                              <1> ;	; 02/05/2016
  5606                              <1> ;	;inc	byte [sysflg] ; 0FFh -> 0
  5607                              <1> ;	;mov	byte [sysflg], 0 ; 04/01/2017
  5608                              <1> ;	movzx	ebx, byte [u.uno]
  5609                              <1> ;	shl	bl, 1 ; 13/11/2017 	
  5610                              <1> ;	cmp	word [ebx+p.ppid-2], 1 ; MainProg
  5611                              <1> ;	ja	sysret0 ; 03/05/2016
  5612                              <1> ;	push	sysret ; * 
  5613                              <1> ;	mov	[u.usp], esp
  5614                              <1> ;	call	wswap ; save child process 'u' structure and
  5615                              <1> ;		      ; registers
  5616                              <1> ;	add	dword [u.usp], 4 ; 03/05/2016 
  5617                              <1> ;sysexec_19: ; 02/05/2016
  5618                              <1> ;	retn ; * 'sysret' ; byte [sysflg] -> 0FFh
  5619                              <1> 
  5620                              <1> readi:
  5621                              <1> 	; 01/05/2016
  5622                              <1> 	; 25/04/2016 - TRDOS 386 (TRDOS v2.0)
  5623                              <1> 	; 20/05/2015 - Retro UNIX 386 v1
  5624                              <1> 	; 11/03/2013 - 31/07/2013 (Retro UNIX 8086 v1)
  5625                              <1> 	;
  5626                              <1> 	; Reads from a file whose the first cluster number in EAX
  5627                              <1> 	; 
  5628                              <1> 	; INPUTS ->
  5629                              <1> 	;    EAX - First cluster number of the file
  5630                              <1> 	;    u.count - byte count user desires
  5631                              <1> 	;    u.base - points to user buffer
  5632                              <1> 	;    u.fofp - points to dword with current file offset
  5633                              <1> 	;    i.size - file size
  5634                              <1> 	;    cdev - logical dos drive number of the file
  5635                              <1> 	; OUTPUTS ->
  5636                              <1> 	;    u.count - cleared
  5637                              <1> 	;    u.nread - accumulates total bytes passed back
  5638                              <1> 	;
  5639                              <1> 	; ((EAX)) input/output
  5640                              <1> 	; (Retro UNIX Prototype : 14/12/2012 - 01/03/2013, UNIXCOPY.ASM)
  5641                              <1>         ; ((Modified registers: edx, ebx, ecx, esi, edi))  
  5642                              <1> 
  5643 0000E898 31D2                <1> 	xor	edx, edx ; 0
  5644 0000E89A 8915[8C030300]      <1> 	mov 	[u.nread], edx ; 0
  5645 0000E8A0 668915[C4030300]    <1> 	mov	[u.pcount], dx ; 19/05/2015
  5646 0000E8A7 3915[88030300]      <1> 	cmp 	[u.count], edx ; 0
  5647 0000E8AD 7701                <1> 	ja 	short readi_1
  5648 0000E8AF C3                  <1> 	retn
  5649                              <1> readi_1:
  5650                              <1> dskr:
  5651                              <1> 	; 01/05/2016
  5652                              <1> 	; 25/04/2016 - TRDOS 386 (TRDOS v2.0)
  5653                              <1> 	; 24/05/2015 - 12/10/2015 (Retro UNIX 386 v1)
  5654                              <1> 	; 26/04/2013 - 03/08/2013 (Retro UNIX 8086 v1)
  5655                              <1> dskr_0:
  5656 0000E8B0 8B15[55040300]      <1>         mov	edx, [i.size]
  5657 0000E8B6 8B1D[74030300]      <1> 	mov	ebx, [u.fofp]
  5658 0000E8BC 2B13                <1> 	sub	edx, [ebx]
  5659 0000E8BE 7647                <1> 	jna	short dskr_4
  5660                              <1> 	;
  5661 0000E8C0 50                  <1> 	push	eax ; 01/05/2016
  5662 0000E8C1 3B15[88030300]      <1> 	cmp     edx, [u.count] 
  5663 0000E8C7 7306                <1> 	jnb	short dskr_1
  5664 0000E8C9 8915[88030300]      <1> 	mov	[u.count], edx
  5665                              <1> dskr_1:
  5666                              <1> 	; EAX = First Cluster
  5667                              <1> 	; [Current_Drv] = Physical drive number 
  5668 0000E8CF E83B000000          <1> 	call	mget_r
  5669                              <1> 	; NOTE: in 'mget_r', relevant sector will be read in buffer
  5670                              <1> 	; if it is not already in buffer !
  5671 0000E8D4 BB[8C050300]        <1> 	mov	ebx, readi_buffer
  5672 0000E8D9 803D[C6030300]00    <1> 	cmp	byte [u.kcall], 0 ; the caller is 'namei' sign (=1)
  5673 0000E8E0 770F                <1> 	ja	short dskr_3	  ; zf=0 -> the caller is 'namei'
  5674 0000E8E2 66833D[C4030300]00  <1> 	cmp	word [u.pcount], 0
  5675 0000E8EA 7705                <1> 	ja	short dskr_3
  5676                              <1> dskr_2:
  5677                              <1> 	; [u.base] = virtual address to transfer (as destination address)
  5678 0000E8EC E894010000          <1> 	call	trans_addr_w ; translate virtual address to physical (w)
  5679                              <1> dskr_3:
  5680                              <1> 	; EBX (r5) = system (I/O) buffer address -physical-
  5681 0000E8F1 E8F7010000          <1> 	call	sioreg
  5682 0000E8F6 87F7                <1> 	xchg	esi, edi
  5683                              <1> 	; EDI = file (user data) offset
  5684                              <1> 	; ESI = sector (I/O) buffer offset
  5685                              <1> 	; ECX = byte count
  5686 0000E8F8 F3A4                <1> 	rep	movsb
  5687                              <1> 	; eax = remain bytes in buffer
  5688                              <1>         ;       (check if remain bytes in the buffer > [u.pcount])
  5689 0000E8FA 09C0                <1> 	or	eax, eax
  5690 0000E8FC 75EE                <1> 	jnz	short dskr_2 ; (page end before system buffer end!)		
  5691 0000E8FE 58                  <1> 	pop	eax  ; (first cluster number)
  5692 0000E8FF 390D[88030300]      <1> 	cmp	[u.count], ecx ; 0
  5693 0000E905 77A9                <1> 	ja	short dskr_0
  5694                              <1> dskr_4:
  5695 0000E907 C605[C6030300]00    <1> 	mov	byte [u.kcall], 0
  5696 0000E90E C3                  <1> 	retn
  5697                              <1> 
  5698                              <1> mget_r:
  5699                              <1> 	; 24/10/2016
  5700                              <1> 	; 22/10/2016
  5701                              <1> 	; 12/10/2016
  5702                              <1> 	; 29/04/2016
  5703                              <1> 	; 25/04/2016 - TRDOS 386 (TRDOS v2.0)
  5704                              <1> 	; 03/06/2015 (Retro UNIX 386 v1, 'mget', u.5s)
  5705                              <1> 	; 22/03/2013 - 31/07/2013 (Retro UNIX 8086 v1)
  5706                              <1> 	;
  5707                              <1> 	; Get existing or (allocate) a new disk block for file
  5708                              <1> 	; 
  5709                              <1> 	; INPUTS ->
  5710                              <1> 	;    [u.fofp] = file offset pointer
  5711                              <1> 	;    EAX = First Cluster
  5712                              <1> 	;    [cdev] = Logical dos drive number 	  
  5713                              <1> 	;    ([u.off] = file offset)
  5714                              <1> 	; OUTPUTS ->
  5715                              <1> 	;    EAX = logical sector number
  5716                              <1> 	;    ESI = Logical Dos Drive Description Table address	
  5717                              <1> 	;
  5718                              <1> 	; Modified registers: EDX, EBX, ECX, ESI, EDI
  5719                              <1> 
  5720 0000E90F 8B35[74030300]      <1> 	mov     esi, [u.fofp]
  5721 0000E915 8B1E                <1> 	mov	ebx, [esi] ; (u.off)
  5722                              <1> 
  5723 0000E917 29C9                <1> 	sub	ecx, ecx
  5724 0000E919 8A2D[46030300]      <1> 	mov	ch, [cdev]
  5725                              <1> 
  5726 0000E91F BE00010900          <1> 	mov	esi, Logical_DOSDisks
  5727 0000E924 01CE                <1> 	add	esi, ecx
  5728                              <1> 
  5729 0000E926 380D[B46A0100]      <1> 	cmp	[readi.valid], cl ; 0
  5730 0000E92C 7649                <1> 	jna	short mget_r_0
  5731                              <1> 	
  5732 0000E92E 3A2D[B56A0100]      <1> 	cmp	ch, [readi.drv]
  5733 0000E934 7541                <1> 	jne	short mget_r_0
  5734                              <1> 
  5735 0000E936 3B05[C86A0100]      <1> 	cmp	eax, [readi.fclust]
  5736 0000E93C 7565                <1> 	jne	short mget_r_3
  5737                              <1> 	
  5738 0000E93E 89D8                <1> 	mov	eax, ebx ; file offset
  5739 0000E940 668B0D[BC6A0100]    <1> 	mov	cx, [readi.bpc]
  5740 0000E947 41                  <1> 	inc	ecx ; <= 65536
  5741 0000E948 29D2                <1> 	sub	edx, edx
  5742 0000E94A F7F1                <1> 	div	ecx
  5743                              <1> 
  5744 0000E94C 8B3D[C46A0100]      <1> 	mov	edi, [readi.c_index] ; cluster index
  5745                              <1> 
  5746 0000E952 39F8                <1> 	cmp	eax, edi
  5747 0000E954 757A                <1>         jne     short mget_r_4  ; (*)
  5748                              <1> 
  5749                              <1> 	; edx = byte offset in cluster (<= 65535)
  5750 0000E956 668915[BE6A0100]    <1> 	mov	[readi.offset], dx
  5751 0000E95D 66C1EA09            <1> 	shr	dx, 9 ; / 512
  5752 0000E961 8815[B76A0100]      <1> 	mov	[readi.s_index], dl ; sector index in cluster (0 to spc -1)
  5753                              <1> 	
  5754 0000E967 A1[C06A0100]        <1> 	mov	eax, [readi.cluster]  ; > 0 if [readi.valid] = 1
  5755 0000E96C 8B15[CC6A0100]      <1> 	mov	edx, [readi.fs_index]
  5756 0000E972 E99A000000          <1>         jmp     mget_r_7
  5757                              <1> 	
  5758                              <1> mget_r_0:
  5759 0000E977 882D[B56A0100]      <1> 	mov	[readi.drv], ch ; physical drive number
  5760 0000E97D 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  5761 0000E981 7707                <1> 	ja	short mget_r_1
  5762 0000E983 8A4E12              <1> 	mov	cl, [esi+LD_FS_BytesPerSec+1]
  5763 0000E986 D0E9                <1> 	shr	cl, 1 ;  ; 1 for 512 bytes, 4 for 2048 bytes
  5764 0000E988 EB03                <1> 	jmp	short mget_r_2	
  5765                              <1> mget_r_1:
  5766 0000E98A 8A4E13              <1> 	mov	cl, [esi+LD_BPB+BPB_SecPerClust]
  5767                              <1> mget_r_2:
  5768 0000E98D 880D[B66A0100]      <1> 	mov	[readi.spc], cl  ; sectors per cluster
  5769                              <1> 	; NOTE: readi bytes per sector value is always 512 ! 
  5770 0000E993 66C1E109            <1> 	shl	cx, 9 ; * 512
  5771 0000E997 6649                <1> 	dec	cx ; bytes per cluster - 1
  5772 0000E999 66890D[BC6A0100]    <1> 	mov	[readi.bpc], cx
  5773 0000E9A0 6629C9              <1> 	sub	cx, cx
  5774                              <1> mget_r_3:
  5775 0000E9A3 A3[C86A0100]        <1> 	mov	[readi.fclust], eax ; first cluster (or FDT address)
  5776 0000E9A8 880D[B46A0100]      <1> 	mov	[readi.valid], cl ; 0 
  5777                              <1> 	;mov	[readi.s_index], cl ; 0
  5778                              <1> 	;mov	[readi.offset], cx ; 0
  5779 0000E9AE 890D[C46A0100]      <1> 	mov	[readi.c_index], ecx ; 0
  5780 0000E9B4 890D[C06A0100]      <1> 	mov	[readi.cluster], ecx ; 0
  5781 0000E9BA 890D[B86A0100]      <1> 	mov	[readi.sector], ecx ; 0
  5782                              <1> 	
  5783 0000E9C0 89D8                <1> 	mov	eax, ebx ; file offset
  5784 0000E9C2 668B0D[BC6A0100]    <1> 	mov	cx, [readi.bpc]
  5785 0000E9C9 41                  <1> 	inc	ecx ; <= 65536
  5786 0000E9CA 29D2                <1> 	sub	edx, edx
  5787 0000E9CC F7F1                <1> 	div	ecx
  5788                              <1> 	;mov	edi, [readi.c_index] ; previous cluster index
  5789 0000E9CE 29FF                <1> 	sub	edi, edi
  5790                              <1> mget_r_4:
  5791 0000E9D0 A3[C46A0100]        <1> 	mov	[readi.c_index], eax ; cluster index
  5792                              <1> 	; edx = byte offset in cluster (<= 65535)
  5793 0000E9D5 668915[BE6A0100]    <1> 	mov	[readi.offset], dx
  5794 0000E9DC 66C1EA09            <1> 	shr	dx, 9 ; / 512
  5795 0000E9E0 8815[B76A0100]      <1> 	mov	[readi.s_index], dl ; sector index in cluster (0 to spc -1)
  5796                              <1> 
  5797 0000E9E6 89C1                <1> 	mov	ecx, eax ; current cluster index
  5798 0000E9E8 A1[C86A0100]        <1> 	mov	eax, [readi.fclust]
  5799 0000E9ED 09C9                <1> 	or	ecx, ecx ; cluster index
  5800 0000E9EF 741B                <1> 	jz	short mget_r_6
  5801                              <1> 
  5802 0000E9F1 39CF                <1> 	cmp	edi, ecx
  5803 0000E9F3 7710                <1> 	ja	short mget_r_5 ; old cluster index is higher
  5804 0000E9F5 8B15[C06A0100]      <1> 	mov	edx, [readi.cluster]
  5805 0000E9FB 21D2                <1> 	and	edx, edx
  5806 0000E9FD 7406                <1> 	jz	short mget_r_5
  5807                              <1> 	; valid 'readi' parameters (*)
  5808 0000E9FF 89D0                <1> 	mov	eax, edx
  5809 0000EA01 29F9                <1> 	sub	ecx, edi
  5810 0000EA03 740C                <1> 	jz	short mget_r_7
  5811                              <1> mget_r_5:
  5812                              <1> 	; EAX = Beginning cluster
  5813                              <1> 	; EDX = Sector index in disk/file section
  5814                              <1> 	;	(Only for SINGLIX file system!)
  5815                              <1> 	; ECX = Cluster sequence number after the beginning cluster
  5816                              <1> 	; ESI = Logical DOS Drive Description Table address
  5817 0000EA05 E809E4FFFF          <1> 	call	get_cluster_by_index
  5818 0000EA0A 724E                <1> 	jc	short mget_r_err
  5819                              <1> 	; EAX = Cluster number		
  5820                              <1> mget_r_6:
  5821 0000EA0C A3[C06A0100]        <1> 	mov	[readi.cluster], eax ; FDT number for Singlix File System
  5822                              <1> mget_r_7:
  5823 0000EA11 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  5824 0000EA15 765F                <1> 	jna	short mget_r_12
  5825                              <1> 
  5826 0000EA17 83E802              <1> 	sub	eax, 2
  5827 0000EA1A 0FB615[B66A0100]    <1> 	movzx	edx, byte [readi.spc]
  5828 0000EA21 F7E2                <1> 	mul	edx
  5829                              <1> 
  5830 0000EA23 034668              <1> 	add	eax, [esi+LD_DATABegin]
  5831 0000EA26 8A15[B76A0100]      <1> 	mov	dl, [readi.s_index]
  5832 0000EA2C 01D0                <1> 	add	eax, edx
  5833                              <1> mget_r_8:
  5834                              <1> 	; eax = logical sector number
  5835 0000EA2E 803D[B46A0100]00    <1> 	cmp	byte [readi.valid], 0
  5836 0000EA35 7608                <1> 	jna	short mget_r_9
  5837 0000EA37 3B05[B86A0100]      <1> 	cmp	eax, [readi.sector]
  5838 0000EA3D 7436                <1> 	je	short mget_r_11 ; sector is already in 'readi' buffer
  5839                              <1> mget_r_9:
  5840 0000EA3F A3[B86A0100]        <1> 	mov	[readi.sector], eax
  5841 0000EA44 BB[8C050300]        <1> 	mov	ebx, readi_buffer ; buffer address
  5842 0000EA49 B901000000          <1> 	mov	ecx, 1
  5843                              <1> 	; 29/04/2016
  5844                              <1> 	;xor	dl, dl
  5845                              <1> 
  5846                              <1> 	; EAX = Logical sector number
  5847                              <1> 	; ECX = Sector count
  5848                              <1> 	; EBX = Buffer address
  5849                              <1> 	; (EDX = 0)
  5850                              <1> 	; ESI = Logical DOS drive description table address	
  5851                              <1> 
  5852 0000EA4E E86E130000          <1> 	call	disk_read
  5853 0000EA53 7314                <1> 	jnc	short mget_r_10
  5854                              <1> 
  5855                              <1> 	; 22/10/2016 (15h -> 17)
  5856 0000EA55 B811000000          <1> 	mov	eax, 17 ; Drive not ready or read error !
  5857                              <1> mget_r_err:
  5858 0000EA5A A3[C8030300]        <1> 	mov	[u.error], eax
  5859                              <1> 	; 12/10/2016
  5860 0000EA5F A3[64030300]        <1> 	mov	[u.r0], eax
  5861 0000EA64 E911E5FFFF          <1> 	jmp	error
  5862                              <1> mget_r_10:
  5863 0000EA69 C605[B46A0100]01    <1> 	mov	byte [readi.valid], 1 ; 24/10/2016
  5864 0000EA70 A1[B86A0100]        <1> 	mov	eax, [readi.sector]
  5865                              <1> mget_r_11:
  5866 0000EA75 C3                  <1> 	retn
  5867                              <1> mget_r_12:
  5868                              <1> 	; EAX = FDT number
  5869                              <1> 	; EDX = Sector index from FDT sector (0,1,2,3,4...)
  5870 0000EA76 40                  <1> 	inc	eax ; the first data sector in FS disk section	
  5871 0000EA77 8915[CC6A0100]      <1> 	mov	[readi.fs_index], edx
  5872 0000EA7D 01D0                <1> 	add	eax, edx
  5873 0000EA7F EBAD                <1> 	jmp	short mget_r_8
  5874                              <1> 
  5875                              <1> trans_addr_r:
  5876                              <1> 	; 12/10/2016
  5877                              <1> 	; 02/05/2016 - TRDOS 386 (TRDOS v2.0)
  5878                              <1> 	; Translate virtual address to physical address 
  5879                              <1> 	; for reading from user's memory space
  5880                              <1> 	; 04/06/2015 - 18/10/2015 (Retro UNIX 386 v1)
  5881                              <1> 
  5882 0000EA81 31D2                <1> 	xor	edx, edx ; 0 (read access sign)
  5883 0000EA83 EB04                <1> 	jmp 	short trans_addr_rw
  5884                              <1> 
  5885                              <1> trans_addr_w:
  5886                              <1> 	; 12/10/2016
  5887                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  5888                              <1> 	; Translate virtual address to physical address 
  5889                              <1> 	; for writing to user's memory space
  5890                              <1> 	; 04/06/2015 - 18/10/2015 (Retro UNIX 386 v1)
  5891                              <1> 	
  5892 0000EA85 29D2                <1> 	sub	edx, edx
  5893 0000EA87 FEC2                <1> 	inc	dl ; 1 (write access sign)
  5894                              <1> trans_addr_rw:
  5895 0000EA89 50                  <1> 	push	eax
  5896 0000EA8A 53                  <1> 	push	ebx
  5897 0000EA8B 52                  <1> 	push 	edx ; r/w sign (in DL)
  5898                              <1> 	;
  5899 0000EA8C 8B1D[84030300]      <1> 	mov	ebx, [u.base]
  5900 0000EA92 E8636FFFFF          <1> 	call	get_physical_addr ; get physical address
  5901 0000EA97 730F                <1> 	jnc	short passc_0
  5902 0000EA99 A3[C8030300]        <1> 	mov	[u.error], eax
  5903 0000EA9E A3[64030300]        <1> 	mov	[u.r0], eax ; 12/10/2016
  5904                              <1> 	;pop	edx
  5905                              <1> 	;pop 	ebx
  5906                              <1> 	;pop	eax
  5907 0000EAA3 E9D2E4FFFF          <1> 	jmp	error
  5908                              <1> passc_0:
  5909 0000EAA8 F6C202              <1> 	test	dl, PTE_A_WRITE ; writable page
  5910 0000EAAB 5A                  <1> 	pop	edx
  5911 0000EAAC 751C                <1> 	jnz	short passc_1
  5912                              <1> 	
  5913 0000EAAE 20D2                <1> 	and 	dl, dl
  5914 0000EAB0 7418                <1> 	jz	short passc_1
  5915                              <1> 	; read only (duplicated) page -must be copied to a new page-
  5916                              <1> 	; EBX = linear address
  5917 0000EAB2 51                  <1> 	push 	ecx
  5918 0000EAB3 E8DB6BFFFF          <1> 	call 	copy_page
  5919 0000EAB8 59                  <1> 	pop	ecx
  5920 0000EAB9 721E                <1> 	jc	short passc_2
  5921 0000EABB 50                  <1> 	push	eax ; physical address of the new/allocated page
  5922 0000EABC E8636EFFFF          <1> 	call	add_to_swap_queue	
  5923 0000EAC1 58                  <1> 	pop	eax
  5924 0000EAC2 81E3FF0F0000        <1> 	and 	ebx, PAGE_OFF ; 0FFFh
  5925                              <1> 	;mov 	ecx, PAGE_SIZE
  5926                              <1> 	;sub	ecx, ebx 
  5927 0000EAC8 01D8                <1> 	add	eax, ebx  
  5928                              <1> passc_1: 
  5929 0000EACA A3[C0030300]        <1> 	mov 	[u.pbase], eax ; physical address	
  5930 0000EACF 66890D[C4030300]    <1> 	mov	[u.pcount], cx ; remain byte count in page (1-4096)
  5931 0000EAD6 5B                  <1> 	pop	ebx
  5932 0000EAD7 58                  <1> 	pop	eax
  5933 0000EAD8 C3                  <1> 	retn
  5934                              <1> passc_2:
  5935 0000EAD9 B804000000          <1> 	mov	eax, ERR_MINOR_IM ; "Insufficient memory !" error
  5936 0000EADE A3[64030300]        <1> 	mov	[u.r0], eax ; 12/10/2016
  5937 0000EAE3 A3[C8030300]        <1> 	mov	dword [u.error], eax
  5938                              <1> 	;pop 	ebx
  5939                              <1> 	;pop	eax
  5940 0000EAE8 E98DE4FFFF          <1> 	jmp	error
  5941                              <1> 
  5942                              <1> sioreg: 
  5943                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  5944                              <1> 	; 19/05/2015 - 25/07/2015 (Retro UNIX 386 v1)
  5945                              <1> 	; 12/03/2013 - 22/07/2013 (Retro UNIX 8086 v1)
  5946                              <1> 	; INPUTS -> 
  5947                              <1> 	;     EBX = system buffer (data) address (r5)
  5948                              <1> 	;     [u.fofp] = pointer to file offset pointer
  5949                              <1> 	;     [u.base] = virtual address of the user buffer
  5950                              <1> 	;     [u.pbase] = physical address of the user buffer
  5951                              <1> 	;     [u.count] = byte count
  5952                              <1> 	;     [u.pcount] = byte count within page frame 			
  5953                              <1> 	; OUTPUTS -> 
  5954                              <1> 	;     ESI = user data offset (r1)
  5955                              <1> 	;     EDI = system (I/O) buffer offset (r2)
  5956                              <1> 	;     ECX = byte count (r3)
  5957                              <1> 	;     EAX = remain bytes after byte count within page frame
  5958                              <1> 	;	(If EAX > 0, transfer will continue from the next page)
  5959                              <1>         ;
  5960                              <1> 	; ((Modified registers:  EDX))
  5961                              <1>  
  5962 0000EAED 8B35[74030300]      <1>         mov     esi, [u.fofp]
  5963 0000EAF3 8B3E                <1>         mov     edi, [esi]
  5964 0000EAF5 89F9                <1> 	mov	ecx, edi
  5965 0000EAF7 81C900FEFFFF        <1> 	or	ecx, 0FFFFFE00h
  5966 0000EAFD 81E7FF010000        <1> 	and	edi, 1FFh
  5967 0000EB03 01DF                <1> 	add	edi, ebx ; EBX = system buffer (data) address
  5968 0000EB05 F7D9                <1> 	neg	ecx
  5969 0000EB07 3B0D[88030300]      <1> 	cmp	ecx, [u.count]
  5970 0000EB0D 7606                <1> 	jna	short sioreg_0
  5971 0000EB0F 8B0D[88030300]      <1> 	mov	ecx, [u.count]
  5972                              <1> sioreg_0:
  5973 0000EB15 803D[C6030300]00    <1> 	cmp	byte [u.kcall], 0 
  5974 0000EB1C 7613                <1> 	jna	short sioreg_1
  5975                              <1> 	 ; the caller is 'mkdir' or 'namei'
  5976 0000EB1E A1[84030300]        <1> 	mov	eax, [u.base]
  5977 0000EB23 A3[C0030300]        <1> 	mov 	[u.pbase], eax ; physical address = virtual address
  5978 0000EB28 66890D[C4030300]    <1> 	mov	word [u.pcount], cx ; remain bytes in buffer (1 sector)
  5979 0000EB2F EB0B                <1> 	jmp	short sioreg_2
  5980                              <1> sioreg_1:
  5981 0000EB31 0FB715[C4030300]    <1> 	movzx	edx, word [u.pcount]
  5982 0000EB38 39D1                <1> 	cmp	ecx, edx	
  5983 0000EB3A 772A                <1> 	ja	short sioreg_4 ; transfer count > [u.pcount]
  5984                              <1> sioreg_2: ; 2:
  5985 0000EB3C 31C0                <1> 	xor 	eax, eax
  5986                              <1> sioreg_3:
  5987 0000EB3E 010D[8C030300]      <1> 	add 	[u.nread], ecx
  5988 0000EB44 290D[88030300]      <1> 	sub 	[u.count], ecx
  5989 0000EB4A 010D[84030300]      <1> 	add 	[u.base], ecx
  5990 0000EB50 010E                <1>         add 	[esi], ecx 
  5991 0000EB52 8B35[C0030300]      <1> 	mov	esi, [u.pbase]
  5992 0000EB58 66290D[C4030300]    <1> 	sub	[u.pcount], cx
  5993 0000EB5F 010D[C0030300]      <1> 	add	[u.pbase], ecx
  5994 0000EB65 C3                  <1>         retn
  5995                              <1> sioreg_4:
  5996                              <1> 	; transfer count > [u.pcount] 
  5997                              <1> 	; (ecx > edx)
  5998 0000EB66 89C8                <1> 	mov	eax, ecx
  5999 0000EB68 29D0                <1> 	sub	eax, edx ; remain bytes for 1 sector (block) transfer 
  6000 0000EB6A 89D1                <1> 	mov	ecx, edx ; current transfer count = [u.pcount]
  6001 0000EB6C EBD0                <1> 	jmp	short sioreg_3
  6002                              <1> 
  6003                              <1> tswitch: ; Retro UNIX 386 v1
  6004                              <1> tswap:
  6005                              <1> 	; 16/01/2017
  6006                              <1> 	; 21/05/2016 - TRDOS 386 (TRDOS v2.0)
  6007                              <1> 	; 10/05/2015 - 01/09/2015 (Retro UNIX 386 v1)
  6008                              <1> 	; 14/04/2013 - 14/02/2014 (Retro UNIX 8086 v1)
  6009                              <1> 	; time out swap, called when a user times out.
  6010                              <1> 	; the user is put on the low priority queue.
  6011                              <1> 	; This is done by making a link from the last user
  6012                              <1> 	; on the low priority queue to him via a call to 'putlu'.
  6013                              <1> 	; then he is swapped out.
  6014                              <1> 
  6015                              <1> 	; TRDOS 386 (TRDOS v2.0) modification ->  ** 21/05/2016 **
  6016                              <1> 	;     * when a high priority (event) process will be stopped
  6017                              <1> 	;	(swapped out, swithched out/off), 'tswap/tswitch' will
  6018                              <1> 	;	not add it to a run queue. 
  6019                              <1> 	;	/// What for: Process may be already in a run queue, 
  6020                              <1> 	;	it is unspeficied state because process might be started
  6021                              <1> 	;	by a timer event which does not regard previous priority
  6022                              <1> 	;	level and run queue of the process (for fast executing!).
  6023                              <1> 	;	After the 'run for event', process will be sequenced
  6024                              <1> 	;	to run by it's actual run queue. ///
  6025                              <1> 	;
  6026                              <1> 	; Retro UNIX 386 v1 modification ->
  6027                              <1> 	;       swap (software task switch) is performed by changing
  6028                              <1> 	;	user's page directory (u.pgdir) instead of segment change
  6029                              <1> 	;	as in Retro UNIX 8086 v1.
  6030                              <1> 	;
  6031                              <1> 	; RETRO UNIX 8086 v1 modification ->
  6032                              <1> 	;       'swap to disk' is replaced with 'change running segment'
  6033                              <1> 	;	according to 8086 cpu (x86 real mode) architecture.
  6034                              <1> 	;	pdp-11 was using 64KB uniform memory while IBM PC
  6035                              <1> 	;	compatibles was using 1MB segmented memory 
  6036                              <1> 	;	in 8086/8088 times.
  6037                              <1> 	;
  6038                              <1> 	; INPUTS ->
  6039                              <1> 	;    u.uno - users process number
  6040                              <1> 	;    runq+4 - lowest priority queue
  6041                              <1> 	; OUTPUTS ->
  6042                              <1> 	;    r0 - users process number
  6043                              <1> 	;    r2 - lowest priority queue address
  6044                              <1> 	;
  6045                              <1> 	; ((AX = R0, BX = R2)) output
  6046                              <1> 	; ((Modified registers: EDX, EBX, ECX, ESI, EDI))  	
  6047                              <1> 	;
  6048                              <1> 
  6049                              <1> 	NOTE:
  6050                              <1> 	;* [u.pri] priority level is specified by run queue which is process 
  6051                              <1> 	;  comes to run from.
  6052                              <1> 	;* Initial [u.pri] is 1 ('normal/regular') for programs 
  6053                              <1> 	;  (which are launched by MainProg or 'sysexec'), it is changed
  6054                              <1> 	;  to 2 ('high') by timer event, if program uses 'systimer' system call.
  6055                              <1> 	;* Program (Process) also can change it's running priority 
  6056                              <1> 	;  from 1 to 0 or up to 2 by using 'syspri' system call; but,
  6057                              <1> 	;  if program selects priority level 2 (high) for running, next time 
  6058                              <1> 	;  it is reduced to 1 (normal/regular) because 'syspri' adds this
  6059                              <1> 	;  program to 'run for normal' queue while running duration is a bit
  6060                              <1> 	;  protected from swap/switch out immediate, behalf of other high 
  6061                              <1> 	;  priority process in sequence. Program (with high priority) will not 
  6062                              <1> 	;  be swapped/switched out (by timer event) before it's time quantum 
  6063                              <1> 	;  will be elapsed, but, this will be temporary if program is not using 
  6064                              <1> 	;  timer event function.	  			 	
  6065                              <1> 
  6066                              <1> 	;For example:
  6067                              <1> 	;If a process frequently gets a timer event, it runs at high priority
  6068                              <1> 	;level but when it returns from running it returns to actual run queue,
  6069                              <1> 	;not to 'run for event' queue again.
  6070                              <1> 	;'tswap' will not change the sequence at return/stop(swap out) stage.
  6071                              <1> 	;But if priority level not high (=2, 'run for event'), 'tswap/tswitch'
  6072                              <1> 	;will add the stopping process to relevant run queue according to
  6073                              <1> 	;[u.pri] priority level.
  6074                              <1> 
  6075                              <1> 	; 16/01/2017
  6076 0000EB6E BB[54030300]        <1> 	mov	ebx, runq+2 	; 'runq_normal' ; normal/regular priority
  6077                              <1> 	; 21/05/2016
  6078                              <1> 	;cmp	byte [u.pri], 2	; high priority (run for event) ?
  6079                              <1> 	;jnb	short swap
  6080                              <1> 	; 16/01/2017
  6081                              <1> 	; (Normal and also high/event priority processes will be added to
  6082                              <1> 	; normal priority run queue for ensuring circular running sequence!)
  6083                              <1> 	; (Timer interrupt or 'syspri' system call may change priority and run
  6084                              <1> 	; queue to high/event level.)
  6085 0000EB73 803D[A9030300]00    <1> 	cmp	byte [u.pri], 0
  6086 0000EB7A 7702                <1> 	ja	short tswap_1	; normal priority run queue
  6087                              <1> 	;
  6088 0000EB7C 43                  <1> 	inc	ebx
  6089 0000EB7D 43                  <1> 	inc	ebx		; runq+4, 'runq_background', low priority
  6090                              <1> tswap_1:
  6091 0000EB7E A0[B3030300]        <1> 	mov 	al, [u.uno]
  6092                              <1> 	       	; movb u.uno,r1 / move users process number to r1
  6093                              <1> 		; mov  $runq+4,r2 
  6094                              <1> 			; / move lowest priority queue address to r2
  6095                              <1>       	; ebx = run queue
  6096 0000EB83 E8FE000000          <1> 	call 	putlu
  6097                              <1> 		; jsr r0,putlu / create link from last user on Q to 
  6098                              <1> 		             ; / u.uno's user
  6099                              <1> 
  6100                              <1> switch: ; Retro UNIX 386 v1
  6101                              <1> swap:
  6102                              <1> 	; 02/01/2017
  6103                              <1> 	; 21/05/2016
  6104                              <1> 	; 20/05/2016
  6105                              <1> 	; 02/05/2016
  6106                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  6107                              <1> 	; 10/05/2015 - 02/09/2015 (Retro UNIX 386 v1)
  6108                              <1> 	; 14/04/2013 - 08/03/2014 (Retro UNIX 8086 v1)
  6109                              <1> 	;
  6110                              <1> 	; 'swap' is routine that controls the swapping of processes
  6111                              <1> 	; in and out of core.
  6112                              <1> 	;
  6113                              <1> 	; TRDOS 386 (TRDOS v2.0) modification ->  ** 20/05/2016 **
  6114                              <1> 	;     * 3 different priority level is applied 
  6115                              <1> 	;	(just as original unix v1)
  6116                              <1> 	;	1) high priority (event) run queue, 'runq_event'
  6117                              <1> 	;	2) normal priority (regular) run queue, 'runq_normal'
  6118                              <1> 	;	3) low priority (background) run queue, 'runq_backgroud'
  6119                              <1> 	;	'swap' code will run a process which has max. priority
  6120                              <1>         ;       (for earliest event at first)
  6121                              <1> 	;
  6122                              <1> 	; Retro UNIX 386 v1 modification ->
  6123                              <1> 	;       swap (software task switch) is performed by changing
  6124                              <1> 	;	user's page directory (u.pgdir) instead of segment change
  6125                              <1> 	;	as in Retro UNIX 8086 v1.
  6126                              <1> 	;
  6127                              <1> 	; RETRO UNIX 8086 v1 modification ->
  6128                              <1> 	;       'swap to disk' is replaced with 'change running segment'
  6129                              <1> 	;	according to 8086 cpu (x86 real mode) architecture.
  6130                              <1> 	;	pdp-11 was using 64KB uniform memory while IBM PC
  6131                              <1> 	;	compatibles was using 1MB segmented memory 
  6132                              <1> 	;	in 8086/8088 times.
  6133                              <1> 	;
  6134                              <1> 	; INPUTS ->
  6135                              <1> 	;    runq table - contains processes to run.
  6136                              <1> 	;    p.link - contains next process in line to be run.
  6137                              <1> 	;    u.uno - process number of process in core	
  6138                              <1> 	;    s.stack - swap stack used as an internal stack for swapping.	
  6139                              <1> 	; OUTPUTS ->
  6140                              <1> 	;    (original unix v1 -> present process to its disk block)
  6141                              <1> 	;    (original unix v1 -> new process into core -> 
  6142                              <1> 	;	   Retro Unix 8086 v1 -> segment registers changed 
  6143                              <1> 	;	   for new process)
  6144                              <1> 	;    u.quant = 3 (Time quantum for a process)
  6145                              <1> 	; 	((INT 1Ch count down speed -> 18.2 times per second)	 	
  6146                              <1> 	;    RETRO UNIX 8086 v1 will use INT 1Ch (18.2 times per second)
  6147                              <1> 	;	 for now, it will swap the process if there is not
  6148                              <1> 	;	 a keyboard event (keystroke) (Int 15h, function 4Fh)
  6149                              <1> 	;	 or will count down from 3 to 0 even if there is a
  6150                              <1> 	;        keyboard event locking due to repetitive key strokes.
  6151                              <1> 	;	 u.quant will be reset to 3 for RETRO UNIX 8086 v1.
  6152                              <1> 	;
  6153                              <1> 	; ((Modified registers: EAX, EDX, EBX, ECX, ESI, EDI))  	
  6154                              <1> 
  6155                              <1> 	;NOTE:
  6156                              <1> 	;High priority queue is the first for selecting a process to run.
  6157                              <1> 	;If there is not a process in high priority level run queue,
  6158                              <1> 	;a process in normal priority run queue will be selected
  6159                              <1> 	;or a proces in low priority run queue will be selected if normal
  6160                              <1> 	;priority level run queue is empty.
  6161                              <1> 	
  6162                              <1> 	; 21/05/2016 -(3 priority levels, 3 run queues)
  6163 0000EB88 BE[52030300]        <1> 	mov	esi, runq ; 'runq_event' ; high priority, 'run for event'
  6164 0000EB8D C605[106B0100]03    <1> 	mov	byte [priority], 3 ; high priority + 1
  6165 0000EB94 31DB                <1> 	xor	ebx, ebx ; 02/01/2017
  6166                              <1> swap_0: ; 1: / search runq table for highest priority process
  6167 0000EB96 66AD                <1> 	lodsw  ; mov ax, [esi], add esi+2
  6168                              <1> 	;xor	ebx, ebx ; 02/05/2016
  6169 0000EB98 6621C0              <1> 	and 	ax, ax ; are there any processes to run in this Q entry
  6170 0000EB9B 750E                <1> 	jnz	short swap_2 
  6171                              <1> 	; 21/05/2026
  6172                              <1> 	; runq_normal = runq+2, runq_background = runq+4
  6173 0000EB9D FE0D[106B0100]      <1> 	dec	byte [priority] ; 3 -> 3, 2 -> 1, 1-> 0
  6174 0000EBA3 75F1                <1> 	jnz	short swap_0	
  6175                              <1> 	;cmp	esi, runq+6  ; if zero compare address to end of table
  6176                              <1> 	;jb	short swap_0 ; if not at end, go back
  6177                              <1> swap_1:
  6178                              <1> 	; 02/05/2016
  6179                              <1> 	; 29/04/2016 (TRDOS 386 = TRDOS v2.0)
  6180                              <1> 	; No user process to run...
  6181                              <1> 	; Run the kernel process... MainProg: Internal Command Interpreter  
  6182 0000EBA5 FEC0                <1> 	inc	al ; mov al, 1  ; process number of MainProg
  6183 0000EBA7 FEC3                <1> 	inc	bl ; mov bl, al ; 1
  6184 0000EBA9 EB1E                <1> 	jmp	short swap_4
  6185                              <1> swap_2:
  6186                              <1> 	; 21/05/2016
  6187 0000EBAB FE0D[106B0100]      <1> 	dec	byte [priority] ; priority level of present user/process
  6188                              <1> 			        ; 0, 1, 2	   
  6189 0000EBB1 4E                  <1> 	dec	esi
  6190 0000EBB2 4E                  <1>         dec     esi
  6191                              <1> 	;
  6192 0000EBB3 88C3                <1> 	mov	bl, al
  6193 0000EBB5 38E0                <1> 	cmp	al, ah ; is there only 1 process in the queue to be run
  6194 0000EBB7 740A                <1> 	je	short swap_3 ; yes
  6195 0000EBB9 8AA3[9F000300]      <1> 	mov	ah, [ebx+p.link-1] 
  6196 0000EBBF 8826                <1>        	mov	[esi], ah ; move next process in line into run queue
  6197 0000EBC1 EB06                <1> 	jmp	short swap_4
  6198                              <1> swap_3: 
  6199 0000EBC3 6631D2              <1> 	xor	dx, dx
  6200 0000EBC6 668916              <1> 	mov	[esi], dx ; zero the entry; no processes on the Q
  6201                              <1> swap_4: 
  6202 0000EBC9 8A25[B3030300]      <1> 	mov 	ah, [u.uno]
  6203 0000EBCF 38C4                <1> 	cmp	ah, al ; is this process the same as the process in core?
  6204 0000EBD1 743B                <1>        	je	short swap_8 ; yes, don't have to swap
  6205 0000EBD3 08E4                <1> 	or	ah, ah  ; is the process # = 0
  6206 0000EBD5 740D                <1>        	jz	short swap_6 ; 'sysexit'
  6207                              <1> 	;cmp	ah, al ;is this process the same as the process in core?
  6208                              <1>        	;je	short swap_8 ; yes, don't have to swap
  6209 0000EBD7 8925[60030300]      <1> 	mov	[u.usp], esp ; return  address for 'syswait' & 'sleep'
  6210 0000EBDD E834000000          <1> 	call	wswap   ; write out core to disk
  6211 0000EBE2 EB1C                <1> 	jmp 	short swap_7
  6212                              <1> swap_6:
  6213                              <1> 	; Deallocate memory pages belong to the process
  6214                              <1> 	; which is being terminated.
  6215                              <1> 	; (Retro UNIX 386 v1 modification !)
  6216                              <1> 	;
  6217 0000EBE4 53                  <1> 	push	ebx
  6218 0000EBE5 A1[B8030300]        <1> 	mov 	eax, [u.pgdir]  ; page directory of the process
  6219 0000EBEA 8B1D[BC030300]      <1> 	mov	ebx, [u.ppgdir] ; page directory of the parent process
  6220 0000EBF0 E82968FFFF          <1> 	call	deallocate_page_dir
  6221 0000EBF5 A1[B4030300]        <1> 	mov	eax, [u.upage] ; 'user' structure page of the process
  6222 0000EBFA E8C468FFFF          <1> 	call	deallocate_page
  6223 0000EBFF 5B                  <1> 	pop	ebx
  6224                              <1> swap_7: 
  6225 0000EC00 C0E302              <1> 	shl	bl, 2 ; * 4 
  6226 0000EC03 8B83[BC000300]      <1> 	mov	eax, [ebx+p.upage-4] ; the 'u' page of the new process
  6227 0000EC09 E840000000          <1> 	call	rswap ; read new process into core
  6228                              <1> swap_8: 
  6229                              <1> 	; Retro UNIX  8086 v1 modification !
  6230 0000EC0E C605[A8030300]04    <1> 	mov	byte [u.quant], time_count 
  6231 0000EC15 C3                  <1> 	retn
  6232                              <1> 
  6233                              <1> wswap:  ; < swap out, swap to disk >
  6234                              <1> 	; 28/02/2017 (fnsave)
  6235                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  6236                              <1> 	; 09/05/2015 (Retro UNIX 386 v1)
  6237                              <1> 	; 26/05/2013 - 08/03/2014 (Retro UNIX 8086 v1)
  6238                              <1> 	; 'wswap' writes out the process that is in core onto its 
  6239                              <1> 	; appropriate disk area.
  6240                              <1> 	;
  6241                              <1> 	; Retro UNIX 386 v1 modification ->
  6242                              <1> 	;       User (u) structure content and the user's register content
  6243                              <1> 	;	will be copied to the process's/user's UPAGE (a page for
  6244                              <1> 	;	saving 'u' structure and user registers for task switching).
  6245                              <1> 	;	u.usp - points to kernel stack address which contains
  6246                              <1> 	;		user's registers while entering system call.  
  6247                              <1> 	;	u.sp  - points to kernel stack address 
  6248                              <1> 	;		to return from system call -for IRET-.
  6249                              <1> 	;	[u.usp]+32+16 = [u.sp] 
  6250                              <1> 	;	[u.usp] -> edi, esi, ebp, esp (= [u.usp]+32), ebx, 
  6251                              <1> 	;		edx, ecx, eax, gs, fs, es, ds, -> [u.sp].
  6252                              <1> 	;
  6253                              <1> 	; Retro UNIX 8086 v1 modification ->
  6254                              <1> 	;       'swap to disk' is replaced with 'change running segment'
  6255                              <1> 	;	according to 8086 cpu (x86 real mode) architecture.
  6256                              <1> 	;	pdp-11 was using 64KB uniform memory while IBM PC
  6257                              <1> 	;	compatibles was using 1MB segmented memory 
  6258                              <1> 	;	in 8086/8088 times.
  6259                              <1> 	;
  6260                              <1> 	; INPUTS ->
  6261                              <1> 	;    u.break - points to end of program
  6262                              <1> 	;    u.usp - stack pointer at the moment of swap
  6263                              <1> 	;    core - beginning of process program		
  6264                              <1> 	;    ecore - end of core 	
  6265                              <1> 	;    user - start of user parameter area		
  6266                              <1> 	;    u.uno - user process number	
  6267                              <1> 	;    p.dska - holds block number of process	
  6268                              <1> 	; OUTPUTS ->
  6269                              <1> 	;    swp I/O queue
  6270                              <1> 	;    p.break - negative word count of process 
  6271                              <1> 	;    r1 - process disk address	
  6272                              <1> 	;    r2 - negative word count
  6273                              <1> 	;
  6274                              <1> 	; RETRO UNIX 8086 v1 input/output:
  6275                              <1> 	;
  6276                              <1> 	; INPUTS ->
  6277                              <1> 	;    u.uno - process number (to be swapped out)
  6278                              <1> 	; OUTPUTS ->
  6279                              <1> 	;    none
  6280                              <1> 	;
  6281                              <1> 	;   ((Modified registers: ECX, ESI, EDI))  
  6282                              <1> 	;
  6283                              <1> 
  6284                              <1> 	; 28/02/2017
  6285                              <1> 	;cmp	byte [multi_tasking], 0  ; Musti tasking mode ?
  6286                              <1> 	;jna	short wswp
  6287 0000EC16 803D[DA030300]00    <1> 	cmp	byte [u.fpsave], 0 ; 28/02/2017
  6288 0000EC1D 7606                <1> 	jna	short wswp
  6289 0000EC1F DD35[DC030300]      <1> 	fnsave	[u.fpregs] ; save floating point registers (94 bytes)
  6290                              <1> wswp:
  6291 0000EC25 8B3D[B4030300]      <1> 	mov	edi, [u.upage] ; process's user (u) structure page addr
  6292 0000EC2B B938000000          <1> 	mov	ecx, (U_SIZE + 3) / 4
  6293 0000EC30 BE[5C030300]        <1> 	mov	esi, user ; active user (u) structure	
  6294 0000EC35 F3A5                <1> 	rep	movsd
  6295                              <1> 	;
  6296 0000EC37 8B35[60030300]      <1> 	mov	esi, [u.usp] ; esp (system stack pointer, 
  6297                              <1> 			     ;      points to user registers)
  6298 0000EC3D 8B0D[5C030300]      <1> 	mov	ecx, [u.sp]  ; return address from the system call
  6299                              <1> 			     ; (for IRET)
  6300                              <1> 			     ; [u.sp] -> EIP (user)
  6301                              <1> 			     ; [u.sp+4]-> CS (user)
  6302                              <1> 			     ; [u.sp+8] -> EFLAGS (user)
  6303                              <1> 			     ; [u.sp+12] -> ESP (user)
  6304                              <1> 			     ; [u.sp+16] -> SS (user)	
  6305 0000EC43 29F1                <1> 	sub	ecx, esi     ; required space for user registers
  6306 0000EC45 83C114              <1> 	add	ecx, 20	     ; +5 dwords to return from system call
  6307                              <1> 			     ; (for IRET) 	
  6308 0000EC48 C1E902              <1> 	shr	ecx, 2	     		
  6309 0000EC4B F3A5                <1> 	rep	movsd
  6310 0000EC4D C3                  <1> 	retn
  6311                              <1> 
  6312                              <1> rswap:  ; < swap in, swap from disk >
  6313                              <1> 	; 28/02/2017 (frstor)
  6314                              <1> 	; 15/01/2017
  6315                              <1> 	; 14/01/2017
  6316                              <1> 	; 21/05/2016
  6317                              <1> 	; 03/05/2016
  6318                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  6319                              <1> 	; 09/05/2015 - 15/09/2015 (Retro UNIX 386 v1)
  6320                              <1> 	; 26/05/2013 - 08/03/2014 (Retro UNIX 8086 v1)
  6321                              <1> 	; 'rswap' reads a process whose number is in r1, 
  6322                              <1> 	; from disk into core.
  6323                              <1> 	;
  6324                              <1> 	; Retro UNIX 386 v1 modification ->
  6325                              <1> 	;       User (u) structure content and the user's register content
  6326                              <1> 	;	will be restored from process's/user's UPAGE (a page for
  6327                              <1> 	;	saving 'u' structure and user registers for task switching).
  6328                              <1> 	;	u.usp - points to kernel stack address which contains
  6329                              <1> 	;		user's registers while entering system call.  
  6330                              <1> 	;	u.sp  - points to kernel stack address 
  6331                              <1> 	;		to return from system call -for IRET-.
  6332                              <1> 	;	[u.usp]+32+16 = [u.sp] 
  6333                              <1> 	;	[u.usp] -> edi, esi, ebp, esp (= [u.usp]+32), ebx, 
  6334                              <1> 	;		edx, ecx, eax, gs, fs, es, ds, -> [u.sp].
  6335                              <1> 	;
  6336                              <1> 	; RETRO UNIX 8086 v1 modification ->
  6337                              <1> 	;       'swap to disk' is replaced with 'change running segment'
  6338                              <1> 	;	according to 8086 cpu (x86 real mode) architecture.
  6339                              <1> 	;	pdp-11 was using 64KB uniform memory while IBM PC
  6340                              <1> 	;	compatibles was using 1MB segmented memory 
  6341                              <1> 	;	in 8086/8088 times.
  6342                              <1> 	;
  6343                              <1> 	; INPUTS ->
  6344                              <1> 	;    r1 - process number of process to be read in
  6345                              <1> 	;    p.break - negative of word count of process 
  6346                              <1> 	;    p.dska - disk address of the process		
  6347                              <1> 	;    u.emt - determines handling of emt's 	
  6348                              <1> 	;    u.ilgins - determines handling of illegal instructions		
  6349                              <1> 	; OUTPUTS ->
  6350                              <1> 	;    8 = (u.ilgins)
  6351                              <1> 	;    24 = (u.emt)
  6352                              <1> 	;    swp - bit 10 is set to indicate read 
  6353                              <1> 	;		(bit 15=0 when reading is done)	
  6354                              <1> 	;    swp+2 - disk block address
  6355                              <1> 	;    swp+4 - negative word count 	
  6356                              <1> 	;      ((swp+6 - address of user structure)) 
  6357                              <1> 	;
  6358                              <1> 	; RETRO UNIX 8086 v1 input/output:
  6359                              <1> 	;
  6360                              <1> 	; INPUTS ->
  6361                              <1> 	;    AL	- new process number (to be swapped in)	 
  6362                              <1> 	; OUTPUTS ->
  6363                              <1> 	;    none
  6364                              <1> 	;
  6365                              <1> 	;   ((Modified registers: EAX, ECX, ESI, EDI, ESP)) 
  6366                              <1> 	;
  6367                              <1> 	; Retro UNIX 386 v1 - modification ! 14/05/2015
  6368 0000EC4E 89C6                <1> 	mov	esi, eax  ; process's user (u) structure page addr
  6369 0000EC50 B938000000          <1> 	mov	ecx, (U_SIZE + 3) / 4
  6370 0000EC55 BF[5C030300]        <1> 	mov	edi, user ; active user (u) structure	
  6371 0000EC5A F3A5                <1> 	rep	movsd
  6372 0000EC5C 58                  <1> 	pop	eax	; 'rswap' return address
  6373                              <1> 	; 
  6374                              <1> 	;cli
  6375 0000EC5D 8B3D[60030300]      <1> 	mov	edi, [u.usp] ; esp (system stack pointer, 
  6376                              <1> 			     ;     points to user registers)
  6377 0000EC63 89FC                <1> 	mov	esp, edi     ; 14/01/2017
  6378 0000EC65 8B0D[5C030300]      <1> 	mov	ecx, [u.sp]  ; return address from the system call
  6379                              <1> 			     ; (for IRET)
  6380                              <1> 			     ; [u.sp] -> EIP (user)
  6381                              <1> 			     ; [u.sp+4]-> CS (user)
  6382                              <1> 			     ; [u.sp+8] -> EFLAGS (user)
  6383                              <1> 			     ; [u.sp+12] -> ESP (user)
  6384                              <1> 			     ; [u.sp+16] -> SS (user)		
  6385 0000EC6B 29F9                <1> 	sub	ecx, edi     ; required space for user registers
  6386 0000EC6D 83C114              <1> 	add	ecx, 20	     ; +5 dwords to return from system call
  6387                              <1> 			     ; (for IRET) 	
  6388 0000EC70 C1E902              <1> 	shr	ecx, 2	       		
  6389 0000EC73 F3A5                <1> 	rep	movsd
  6390                              <1> 	;mov	esp, [u.usp] ; 15/09/2015
  6391                              <1> 	;sti
  6392                              <1> 	; 28/02/2017
  6393                              <1> 	;cmp	byte [multi_tasking], 0  ; Musti tasking mode ?
  6394                              <1> 	;jna	short rswp_retn
  6395 0000EC75 803D[DA030300]00    <1> 	cmp	byte [u.fpsave], 0
  6396 0000EC7C 7606                <1> 	jna	short rswp_retn
  6397 0000EC7E DD25[DC030300]      <1> 	frstor	[u.fpregs] ; restore floating point regs (94 bytes)
  6398                              <1> rswp_retn:
  6399 0000EC84 50                  <1> 	push	eax	; 'rswap' return address
  6400 0000EC85 C3                  <1> 	retn
  6401                              <1> 
  6402                              <1> putlu: 
  6403                              <1> 	; 20/05/2016
  6404                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  6405                              <1> 	; 10/05/2015 - 12/09/2015 (Retro UNIX 386 v1)
  6406                              <1> 	; 15/04/2013 - 23/02/2014 (Retro UNIX 8086 v1)
  6407                              <1> 	; 'putlu' is called with a process number in r1 and a pointer
  6408                              <1> 	; to lowest priority Q (runq+4) in r2. A link is created from
  6409                              <1> 	; the last process on the queue to process in r1 by putting
  6410                              <1> 	; the process number in r1 into the last process's link.
  6411                              <1> 	;
  6412                              <1> 	; INPUTS ->
  6413                              <1> 	;    r1 - user process number
  6414                              <1> 	;    r2 - points to lowest priority queue 
  6415                              <1> 	;    p.dska - disk address of the process		
  6416                              <1> 	;    u.emt - determines handling of emt's 	
  6417                              <1> 	;    u.ilgins - determines handling of illegal instructions		
  6418                              <1> 	; OUTPUTS ->
  6419                              <1> 	;    r3 - process number of last process on the queue upon
  6420                              <1> 	;	  entering putlu
  6421                              <1> 	;    p.link-1 + r3 - process number in r1
  6422                              <1> 	;    r2 - points to lowest priority queue
  6423                              <1> 	;
  6424                              <1> 	; ((Modified registers: EDX, EBX)) 
  6425                              <1> 	;
  6426                              <1> 	; / r1 = user process no.; r2 points to lowest priority queue
  6427                              <1> 
  6428                              <1> 	; EBX = r2
  6429                              <1> 	; EAX = r1 (AL=r1b)
  6430                              <1> 
  6431                              <1> 	; 20/05/2016
  6432                              <1> 	; AL = process number (1 to 16) // Retro UNIX 8086, 386 v1 // 
  6433                              <1> 	;     (max. 16 processes available for current kernel version) 
  6434                              <1> 	; EBX = run queue address ; 20/05/2016 (TRDOS 386)
  6435                              <1> 		; which is one of following addresses:
  6436                              <1> 		;  1) 'runq_event' high priority run queue	 	
  6437                              <1> 		;  2) 'runq_normal' normal/regular priority run queue
  6438                              <1> 		;  3) 'runq_background' low priority run queue
  6439                              <1> 
  6440                              <1> 	;mov	ebx, runq
  6441 0000EC86 0FB613              <1> 	movzx  	edx, byte [ebx]
  6442 0000EC89 43                  <1> 	inc	ebx
  6443 0000EC8A 20D2                <1> 	and	dl, dl
  6444                              <1> 		; tstb (r2)+ / is queue empty?
  6445 0000EC8C 740A                <1>        	jz	short putlu_1
  6446                              <1> 		; beq 1f / yes, branch
  6447 0000EC8E 8A13                <1> 	mov 	dl, [ebx] ; 12/09/2015
  6448                              <1> 		; movb (r2),r3 / no, save the "last user" process number
  6449                              <1> 			     ; / in r3
  6450 0000EC90 8882[9F000300]      <1>        	mov	[edx+p.link-1], al
  6451                              <1> 		; movb r1,p.link-1(r3) / put pointer to user on 
  6452                              <1> 			     ; / "last users" link
  6453 0000EC96 EB03                <1> 	jmp	short putlu_2
  6454                              <1> 		; br 2f /
  6455                              <1> putlu_1: ; 1:
  6456 0000EC98 8843FF              <1> 	mov	[ebx-1], al
  6457                              <1>        		; movb r1,-1(r2) / user is only user; 
  6458                              <1> 			    ; / put process no. at beginning and at end
  6459                              <1> putlu_2: ; 2: 
  6460 0000EC9B 8803                <1> 	mov	[ebx], al
  6461                              <1>        		; movb r1,(r2) / user process in r1 is now the last entry
  6462                              <1> 			     ; / on the queue
  6463 0000EC9D 88C2                <1> 	mov	dl, al
  6464 0000EC9F 88B2[9F000300]      <1>         mov     [edx+p.link-1], dh ; 0
  6465                              <1> 		; dec r2 / restore r2
  6466 0000ECA5 C3                  <1>         retn
  6467                              <1> 		; rts r0
  6468                              <1> 
  6469                              <1> sysver:
  6470                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
  6471 0000ECA6 C705[64030300]0002- <1> 	mov	dword [u.r0], 200h ; AH = major version, AL = minor version 
  6471 0000ECAE 0000                <1>
  6472 0000ECB0 E9E5E2FFFF          <1> 	jmp	sysret
  6473                              <1> 
  6474                              <1> 
  6475                              <1> syspri: ; change running priority (of the process)
  6476                              <1> 	; 21/05/2016
  6477                              <1> 	; 20/05/2026 - TRDOS 386 (TRDOS v2.0)
  6478                              <1> 	; INPUT ->
  6479                              <1> 	;	BL = priority level
  6480                              <1> 	;	   0 = low running priority (running on background)
  6481                              <1> 	;	   1 = normal/regular priority (running as regular)
  6482                              <1> 	;	   2 = high/event priority (running for event)
  6483                              <1> 	;	   >2 = invalid, it will accepted as 2 (event)
  6484                              <1> 	;	   0FFh = get/return current running priority only	
  6485                              <1> 	; OUTPUT -> 	
  6486                              <1> 	;	* if current [u.pri] < 2
  6487                              <1> 	;	  if BL input < 0FFh ->
  6488                              <1> 	;	     [u.pri] is updated as in BL input (0,1,2)
  6489                              <1> 	;	  if BL input = 0FFh -> AL = [u.pri] (current)
  6490                              <1> 	;	      
  6491                              <1> 	;	* if current [u.pri] = 2
  6492                              <1> 	;	  if BL input < 0FFh -> cf = 1 & AL = 2
  6493                              <1> 	;	  if BL input = 0FFh -> cf = 0 & AL = 2  
  6494                              <1> 	;	
  6495                              <1> 	;	NOTE: 	
  6496                              <1> 	;	If [u.pri] = 2, it can not be changed to 1 or 0;
  6497                              <1> 	;	because, run queue of the running process is unspecified
  6498                              <1> 	;	at this	stage. Process might be started by a timer event
  6499                              <1> 	;	or priority might be changed to high by previous
  6500                              <1> 	;	'syspri' system	call. In both cases, the process is in
  6501                              <1> 	;	'runq_normal' or 'runq_background' queue.
  6502                              <1> 	;	As result of this fact, when the [u.quant] time quantum
  6503                              <1> 	;	of the process is elapsed or 'sysrele' system call is
  6504                              <1> 	;	instructed by the process, 'tswap' ('tswitch') procedure
  6505                              <1> 	;	will be called (to 'swap' or 'switch' out the procedure)
  6506                              <1> 	;	and it will not call 'putlu' to add the (stopping)
  6507                              <1> 	;	process to relevant run queue when [u.pri] = 2.
  6508                              <1> 	;	(Otherwise, it would be possible to add process to
  6509                              <1> 	;	a run queue while it is already in a run queue, wrongly.)
  6510                              <1>   	;
  6511                              <1> 	;	If [u.pri]< 2, 'tswap/tswitch' procedure will call 
  6512                              <1> 	;	'putlu' to add process to relevant run queue
  6513                              <1> 	;	according to [u.pri] value. ('runq_normal' for 1, 
  6514                              <1> 	;	'runq_background' for 0).
  6515                              <1> 	;
  6516                              <1> 	;	If BL input >= 2 and < 0FFh while [u.pri] < 2,
  6517                              <1> 	;	process will be added to 'runq_normal' queue and
  6518                              <1> 	;	[u.pri] will be set to 2. (in 'syspri' system call)
  6519                              <1> 	;
  6520                              <1> 
  6521 0000ECB5 29C0                <1> 	sub	eax, eax ; 0
  6522 0000ECB7 A3[C8030300]        <1> 	mov	[u.error], eax
  6523                              <1> 
  6524 0000ECBC A0[A9030300]        <1> 	mov	al, [u.pri]
  6525 0000ECC1 A3[64030300]        <1> 	mov	[u.r0], eax
  6526                              <1> 
  6527 0000ECC6 FEC3                <1> 	inc	bl
  6528 0000ECC8 0F84CCE2FFFF        <1> 	jz	sysret ; 0FFh -> 0, get priority level
  6529                              <1> 	
  6530 0000ECCE 3C02                <1> 	cmp	al, 2
  6531 0000ECD0 0F83A4E2FFFF        <1> 	jnb	error ; CF = 1 & AL = 2 (& last error = 0)
  6532                              <1> 
  6533 0000ECD6 FECB                <1> 	dec	bl
  6534 0000ECD8 80FB02              <1> 	cmp	bl, 2
  6535 0000ECDB 7602                <1> 	jna	short syspri_1
  6536 0000ECDD B302                <1> 	mov	bl, 2
  6537                              <1> syspri_1:
  6538 0000ECDF 881D[A9030300]      <1> 	mov	[u.pri], bl
  6539 0000ECE5 80FB02              <1> 	cmp	bl, 2
  6540 0000ECE8 0F82ACE2FFFF        <1>         jb      sysret
  6541                              <1> 
  6542                              <1> 	; here...
  6543                              <1> 	; Priority of current process has been changed to high
  6544                              <1> 	; ('run for event') but current process will be added to
  6545                              <1> 	; 'run as normal' queue. ('run for event' high priority
  6546                              <1> 	; queue is under control of timer -& RTC- interrupt only!) 
  6547                              <1> 	;
  6548                              <1> 	; (Otherwise, process can fall into black hole!
  6549                              <1> 	; e.g. if it is not in waiting list and it has not got 
  6550                              <1> 	; a timer event and it is not in a run queue!
  6551                              <1> 	; Because, when [u.pri] is 2, 'tswap/tswitch' will not 
  6552                              <1> 	; add the stopping process to a run queue.)
  6553                              <1> 
  6554 0000ECEE A0[B3030300]        <1> 	mov	al, [u.uno]
  6555 0000ECF3 BB[54030300]        <1> 	mov	ebx, runq_normal ; normal priority !
  6556                              <1> 				 ; [u.pri] is set to high
  6557                              <1> 				 ; but 'runq_event' queue is set
  6558                              <1> 				 ; only by the kernel's timer
  6559                              <1> 				 ; event function (timer interrupt). 
  6560 0000ECF8 E889FFFFFF          <1> 	call	putlu
  6561 0000ECFD E998E2FFFF          <1> 	jmp	sysret
  6562                              <1> 
  6563                              <1> cpass: ; / get next character from user area of core and put it in AL (r1)
  6564                              <1> 	; 02/05/2016 - TRDOS 386 (TRDOS v2.0)
  6565                              <1> 	; 19/05/2015 - 18/10/2015 (Retro UNIX 386 v1)
  6566                              <1> 	; 14/08/2013 - 20/09/2013 (Retro UNIX 8086 v1)
  6567                              <1> 	; INPUTS -> 
  6568                              <1> 	;     [u.base] = virtual address in user area
  6569                              <1> 	;     [u.count] = byte count (max.)
  6570                              <1> 	;     [u.pcount] = byte count in page (0 = reset)		
  6571                              <1> 	; OUTPUTS -> 
  6572                              <1> 	;     AL = the character which is pointed by [u.base]
  6573                              <1> 	;     zf = 1 -> transfer count has been completed	
  6574                              <1>         ;
  6575                              <1> 	; ((Modified registers:  EAX, EDX, ECX))
  6576                              <1> 	;
  6577 0000ED02 833D[88030300]00    <1> 	cmp 	dword [u.count], 0  ; have all the characters been transferred
  6578                              <1> 			    	    ; i.e., u.count, # of chars. left
  6579 0000ED09 763F                <1> 	jna	short cpass_3	    ; to be transferred = 0?) yes, branch
  6580 0000ED0B FF0D[88030300]      <1> 	dec	dword [u.count]	    ; no, decrement u.count
  6581                              <1>         ; 19/05/2015 
  6582                              <1> 	;(Retro UNIX 386 v1 - translation from user's virtual address
  6583                              <1> 	;		      to physical address
  6584 0000ED11 66833D[C4030300]00  <1> 	cmp	word [u.pcount], 0 ; byte count in page = 0 (initial value)
  6585                              <1> 			     ; 1-4095 --> use previous physical base address
  6586                              <1> 			     ; in [u.pbase]
  6587 0000ED19 770E                <1> 	ja	short cpass_1
  6588 0000ED1B 833D[BC030300]00    <1> 	cmp     dword [u.ppgdir], 0 ; is the caller os kernel
  6589 0000ED22 7427                <1>         je      short cpass_k       ; (sysexec, '/etc/init') ?  (MainProg)
  6590 0000ED24 E858FDFFFF          <1> 	call	trans_addr_r
  6591                              <1> cpass_1:
  6592 0000ED29 66FF0D[C4030300]    <1> 	dec	word [u.pcount]
  6593                              <1> cpass_2: 
  6594 0000ED30 8B15[C0030300]      <1> 	mov	edx, [u.pbase]
  6595 0000ED36 8A02                <1> 	mov	al, [edx]	; take the character pointed to 
  6596                              <1> 				; by u.base and put it in r1
  6597 0000ED38 FF05[8C030300]      <1> 	inc	dword [u.nread] ; increment no. of bytes transferred
  6598 0000ED3E FF05[84030300]      <1> 	inc	dword [u.base]  ; increment the buffer address to point to the
  6599                              <1> 			        ; next byte
  6600 0000ED44 FF05[C0030300]      <1> 	inc	dword [u.pbase]
  6601                              <1> cpass_3:
  6602 0000ED4A C3                  <1> 	retn
  6603                              <1> cpass_k:
  6604                              <1> 	; 02/07/2015
  6605                              <1> 	; The caller is os kernel 
  6606                              <1> 	; (get sysexec arguments from kernel's memory space)
  6607 0000ED4B 8B1D[84030300]      <1> 	mov	ebx, [u.base]
  6608 0000ED51 66C705[C4030300]00- <1>         mov     word [u.pcount], PAGE_SIZE ; 4096
  6608 0000ED59 10                  <1>
  6609 0000ED5A 891D[C0030300]      <1> 	mov	[u.pbase], ebx
  6610 0000ED60 EBCE                <1> 	jmp	short cpass_2
  6611                              <1> 
  6612                              <1> transfer_to_user_buffer: ; fast transfer
  6613                              <1> 	; 27/05/2016
  6614                              <1> 	; 16/05/2016 - TRDOS 386 (TRDOS v2.0)
  6615                              <1> 	;
  6616                              <1> 	; INPUT ->
  6617                              <1> 	;	ESI = source address in system space
  6618                              <1> 	;	EDI = user's buffer address
  6619                              <1> 	;	ECX = transfer (byte) count
  6620                              <1> 	;	[u.pgdir] = user's page directory
  6621                              <1> 	; OUTPUT ->
  6622                              <1> 	;	ECX = actual transfer count
  6623                              <1> 	;	cf = 1 -> error
  6624                              <1> 	;	[u.count] = remain byte count
  6625                              <1> 	;
  6626                              <1> 	; Modified registers: eax, ecx
  6627                              <1> 	;
  6628                              <1> 
  6629 0000ED62 21C9                <1> 	and	ecx, ecx
  6630 0000ED64 743B                <1> 	jz	short ttub_4
  6631                              <1> 
  6632 0000ED66 890D[88030300]      <1> 	mov	[u.count], ecx
  6633                              <1> 	
  6634 0000ED6C 57                  <1> 	push	edi
  6635 0000ED6D 56                  <1> 	push	esi
  6636 0000ED6E 53                  <1> 	push	ebx
  6637 0000ED6F 52                  <1> 	push	edx
  6638 0000ED70 51                  <1> 	push	ecx
  6639                              <1> 
  6640 0000ED71 89FB                <1> 	mov	ebx, edi
  6641 0000ED73 81C300004000        <1> 	add	ebx, CORE ; 27/05/2016
  6642                              <1> ttub_1:
  6643                              <1> 	; ebx = virtual (linear) address
  6644                              <1> 	; [u.pgdir] = user's page directory
  6645 0000ED79 E8826CFFFF          <1>        	call	get_physical_addr_x ; get physical address
  6646 0000ED7E 7222                <1> 	jc	short ttub_5
  6647                              <1> 	; eax = physical address 
  6648                              <1> 	; ecx = remain byte count in page (1-4096)
  6649 0000ED80 89C7                <1> 	mov	edi, eax
  6650 0000ED82 A1[88030300]        <1> 	mov	eax, [u.count]
  6651 0000ED87 39C1                <1> 	cmp	ecx, eax
  6652 0000ED89 7602                <1> 	jna	short ttub_2
  6653 0000ED8B 89C1                <1> 	mov	ecx, eax
  6654                              <1> ttub_2:	
  6655 0000ED8D 29C8                <1> 	sub	eax, ecx
  6656 0000ED8F 01CB                <1> 	add	ebx, ecx
  6657 0000ED91 F3A4                <1> 	rep	movsb
  6658 0000ED93 A3[88030300]        <1> 	mov	[u.count], eax
  6659 0000ED98 09C0                <1> 	or	eax, eax
  6660 0000ED9A 75DD                <1> 	jnz	short ttub_1
  6661                              <1> ttub_retn:
  6662                              <1> tfub_retn:
  6663 0000ED9C 59                  <1> 	pop	ecx ; transfer count = actual transfer count
  6664                              <1> ttub_3:
  6665 0000ED9D 5A                  <1> 	pop	edx
  6666 0000ED9E 5B                  <1> 	pop	ebx
  6667 0000ED9F 5E                  <1> 	pop	esi
  6668 0000EDA0 5F                  <1> 	pop	edi
  6669                              <1> ttub_4:
  6670 0000EDA1 C3                  <1> 	retn
  6671                              <1> ttub_5:
  6672 0000EDA2 59                  <1> 	pop	ecx
  6673 0000EDA3 2B0D[88030300]      <1> 	sub	ecx, [u.count] ; actual transfer count
  6674 0000EDA9 F9                  <1> 	stc
  6675 0000EDAA EBF1                <1> 	jmp	short ttub_3
  6676                              <1> 
  6677                              <1> transfer_from_user_buffer: ; fast transfer
  6678                              <1> 	; 27/05/2016
  6679                              <1> 	; 16/05/2016 - TRDOS 386 (TRDOS v2.0)
  6680                              <1> 	;
  6681                              <1> 	; INPUT ->
  6682                              <1> 	;	ESI = user's buffer address
  6683                              <1> 	;	EDI = destination address in system space
  6684                              <1> 	;	ECX = transfer (byte) count
  6685                              <1> 	;	[u.pgdir] = user's page directory
  6686                              <1> 	; OUTPUT ->
  6687                              <1> 	;	ecx = actual transfer count
  6688                              <1> 	;	cf = 1 -> error
  6689                              <1> 	;	[u.count] = remain byte count
  6690                              <1> 	;
  6691                              <1> 	; Modified registers: eax, ecx
  6692                              <1> 	;
  6693                              <1> 
  6694 0000EDAC 21C9                <1> 	and	ecx, ecx
  6695                              <1> 	;jz	short tfub_4
  6696 0000EDAE 74F1                <1> 	jz	short ttub_4
  6697                              <1> 
  6698 0000EDB0 890D[88030300]      <1> 	mov	[u.count], ecx
  6699                              <1> 	
  6700 0000EDB6 57                  <1> 	push	edi
  6701 0000EDB7 56                  <1> 	push	esi
  6702 0000EDB8 53                  <1> 	push	ebx
  6703 0000EDB9 52                  <1> 	push	edx
  6704 0000EDBA 51                  <1> 	push	ecx
  6705                              <1> 
  6706 0000EDBB 89F3                <1> 	mov	ebx, esi
  6707 0000EDBD 81C300004000        <1> 	add	ebx, CORE ; 27/05/2016
  6708                              <1> tfub_1:
  6709                              <1> 	; ebx = virtual (linear) address
  6710                              <1> 	; [u.pgdir] = user's page directory
  6711 0000EDC3 E8386CFFFF          <1>        	call	get_physical_addr_x ; get physical address
  6712                              <1> 	;jc	short tfub_5
  6713 0000EDC8 72D8                <1> 	jc	short ttub_5
  6714                              <1> 	; eax = physical address 
  6715                              <1> 	; ecx = remain byte count in page (1-4096)
  6716 0000EDCA 89C6                <1> 	mov	esi, eax
  6717 0000EDCC A1[88030300]        <1> 	mov	eax, [u.count]
  6718 0000EDD1 39C1                <1> 	cmp	ecx, eax
  6719 0000EDD3 7602                <1> 	jna	short tfub_2
  6720 0000EDD5 89C1                <1> 	mov	ecx, eax
  6721                              <1> tfub_2:	
  6722 0000EDD7 29C8                <1> 	sub	eax, ecx
  6723 0000EDD9 01CB                <1> 	add	ebx, ecx
  6724 0000EDDB F3A4                <1> 	rep	movsb
  6725 0000EDDD A3[88030300]        <1> 	mov	[u.count], eax
  6726 0000EDE2 09C0                <1> 	or	eax, eax
  6727 0000EDE4 75DD                <1> 	jnz	short tfub_1
  6728                              <1> 
  6729 0000EDE6 EBB4                <1> 	jmp	short tfub_retn
  6730                              <1> 
  6731                              <1> ;tfub_retn:
  6732                              <1> ;	pop	ecx ; transfer count = actual transfer count
  6733                              <1> ;tfub_3:
  6734                              <1> ;	pop	edx
  6735                              <1> ;	pop	ebx
  6736                              <1> ;	pop	esi
  6737                              <1> ;	pop	edi
  6738                              <1> ;tfub_4:
  6739                              <1> ;	retn
  6740                              <1> ;tfub_5:
  6741                              <1> ;	pop	ecx
  6742                              <1> ;	sub	ecx, [u.count] ; actual transfer count
  6743                              <1> ;	stc
  6744                              <1> ;	jmp	short tfub_3
  6745                              <1> 
  6746                              <1> sysfff: ; <Find First File>
  6747                              <1> 	; 17/10/2016
  6748                              <1> 	; 16/10/2016
  6749                              <1> 	; 15/10/2016 TRDOS 386 (TRDOS v2.0) feature only ! 
  6750                              <1> 	;           -derived from TRDOS v1.0, INT_21H.ASM-
  6751                              <1> 	;            ("loc_INT21h_find_first_file")
  6752                              <1> 	; TRDOS 8086 (v1.0)
  6753                              <1>         ; 	07/08/2011 
  6754                              <1>         ;	Find First File
  6755                              <1> 	;	INPUT:
  6756                              <1>         ;	    CX= Attributes
  6757                              <1>         ;	    DS:DX= Pointer to filename
  6758                              <1> 	;	MSDOS OUTPUT:
  6759                              <1> 	;	    DTA: (Default address: PSP offset 80h)
  6760                              <1> 	;	    Offset  Descrription
  6761                              <1> 	;	    0	    Reserved for use find next file
  6762                              <1> 	;	    21	    Attribute of file found
  6763                              <1> 	;	    22	    Time stamp of file
  6764                              <1> 	;	    24	    Date stamp of file
  6765                              <1> 	;	    26	    File size in bytes
  6766                              <1> 	;	    30	    Filename and extension (zero terminated)
  6767                              <1> 	;	If cf = 1:
  6768                              <1> 	;	    Error Codes: (in AX)
  6769                              <1> 	;	    	2 - File not found
  6770                              <1> 	;	       18 - No more files  			
  6771                              <1>         ;
  6772                              <1> 	; TRDOS 386 (v2.0) 
  6773                              <1> 	; 15/10/2016
  6774                              <1> 	;	
  6775                              <1>         ; INPUT ->
  6776                              <1>         ;	   CL = File attributes
  6777                              <1> 	;     	      bit 0 (1) - Read only file (R)
  6778                              <1> 	;             bit 1 (1) - Hidden file (H)
  6779                              <1>         ;             bit 2 (1) - System file (R)
  6780                              <1> 	;             bit 3 (1) - Volume label/name (V)
  6781                              <1>         ;             bit 4 (1) - Subdirectory (D)
  6782                              <1> 	;	      bit 5 (1) - File has been archived (A)
  6783                              <1> 	;	   CH = 0 -> Return basic parameters (24 bytes)
  6784                              <1> 	;	   CH > 0 -> Return FindFile structure/table (128 bytes)
  6785                              <1>         ;          EBX = Pointer to filename (ASCIIZ) -path-
  6786                              <1> 	;	   EDX = File parameters buffer address
  6787                              <1> 	;		(buffer size = 24 bytes if CH input = 0)
  6788                              <1> 	;		(buffer size = 128 bytes if CH input > 0)
  6789                              <1> 	;		 
  6790                              <1> 	; OUTPUT ->
  6791                              <1> 	;	   EAX = 0 if CH input > 0
  6792                              <1> 	;	   EAX = First cluster number of file if CH input = 0	
  6793                              <1> 	;	   EDX = File parameters table/structure address
  6794                              <1> 	;	   Basic Parameters:
  6795                              <1> 	;		Offset  Description
  6796                              <1> 	;		------	---------------
  6797                              <1> 	;		0	File Attributes
  6798                              <1> 	;		1	Ambiguous filename chars are used sign
  6799                              <1> 	;			(0 = filename fits exactly with request)
  6800                              <1> 	;			(>0 = ambiguous filename chars are used)
  6801                              <1> 	;	      	2	Time stamp of file
  6802                              <1> 	;		4	Date stamp of file
  6803                              <1> 	;		6	File size in bytes
  6804                              <1> 	;		10	Short Filename (ASCIIZ, max. 13 bytes)
  6805                              <1> 	;		23	Longname Length (1-255) if existing 
  6806                              <1> 	;  
  6807                              <1> 	;          cf = 1 -> Error code in AL
  6808                              <1> 	;
  6809                              <1> 	; Modified Registers: EAX (at the return of system call)
  6810                              <1> 	;  
  6811                              <1> 	; TR-DOS FindFile (FFF) Structure (128 bytes):
  6812                              <1> 	; 09/10/2011 (DIR.ASM) - 10/02/2016 (trdoskx.s)
  6813                              <1> 	;	
  6814                              <1> 	; Offset	Parameter		Size
  6815                              <1> 	; ------	------------------	-------- 
  6816                              <1> 	; 0		FindFile_Drv		1 byte
  6817                              <1> 	; 1		FindFile_Directory	65 bytes
  6818                              <1> 	; 66		FindFile_Name		13 bytes
  6819                              <1> 	; 79		FindFile_LongNameEntryLength 1 byte
  6820                              <1> 	;Above 80 bytes form
  6821                              <1> 	;TR-DOS Source/Destination File FullName Format/Structure
  6822                              <1> 	; 80		FindFile_AttributesMask 1 word
  6823                              <1> 	; 82		FindFile_DirEntry	32 bytes (*)
  6824                              <1> 	; 114		FindFile_DirFirstCluster 1 double word
  6825                              <1> 	; 118		FindFile_DirCluster	1 double word
  6826                              <1> 	; 122		FindFile_DirEntryNumber 1 word
  6827                              <1> 	; 124		FindFile_MatchCounter	1 word
  6828                              <1> 	; 126		FindFile_Reserved	1 word
  6829                              <1>    	; (*) MS-DOS, FAT 12-16-32 classic directory entry (32 bytes)
  6830                              <1> 
  6831                              <1> 	;mov	[u.namep], ebx
  6832                              <1> 	; 16/10/2016
  6833 0000EDE8 8915[306B0100]      <1> 	mov	[FFF_UBuffer], edx
  6834 0000EDEE 66890D[356B0100]    <1> 	mov	[FFF_Attrib], cx ; [FFF_RType] = ch
  6835                              <1> 		    ; Attributes in CL, return data type in CH
  6836 0000EDF5 89DE                <1> 	mov	esi, ebx
  6837                              <1> 	; file name is forced, change directory as temporary
  6838                              <1> 	;mov	ax, 1
  6839                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset ; 17/10/2016
  6840                              <1> 	;call	set_working_path 
  6841 0000EDF7 E8E8130000          <1> 	call	set_working_path_x ; 17/10/2016	
  6842 0000EDFC 731D                <1> 	jnc	short sysfff_0
  6843                              <1>  
  6844 0000EDFE 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  6845 0000EE00 7505                <1> 	jnz	short sysfff_err
  6846                              <1> 
  6847                              <1> 	; eax = 0
  6848 0000EE02 B80C000000          <1> 	mov	eax, ERR_DIR_NOT_FOUND ; Directory not found !
  6849                              <1> sysfff_err:
  6850 0000EE07 A3[64030300]        <1> 	mov	[u.r0], eax
  6851 0000EE0C A3[C8030300]        <1> 	mov	[u.error], eax
  6852 0000EE11 E8A3140000          <1>         call 	reset_working_path
  6853 0000EE16 E95FE1FFFF          <1> 	jmp	error
  6854                              <1> 
  6855                              <1> sysfff_0:
  6856                              <1> 	;sub	ah, ah ; ah = 0
  6857 0000EE1B 8A0424              <1> 	mov	al, [esp]
  6858 0000EE1E 08C0                <1> 	or	al, al
  6859 0000EE20 7412                <1> 	jz	short sysfff_2
  6860 0000EE22 B410                <1> 	mov	ah, 10h
  6861 0000EE24 A808                <1> 	test	al, 08h
  6862 0000EE26 7503                <1> 	jnz	short sysfff_1
  6863 0000EE28 80CC08              <1> 	or	ah, 08h
  6864                              <1> sysfff_1:
  6865 0000EE2B 2410                <1> 	and	al, 10h ; Directory
  6866 0000EE2D 7405                <1> 	jz	short sysfff_2
  6867 0000EE2F 80E408              <1> 	and	ah, 08h
  6868 0000EE32 30C0                <1> 	xor	al, al ; When a directory is searched,
  6869                              <1> 		       ; filename will be returned even if
  6870                              <1> 		       ; it is not a directory!
  6871                              <1> 		       ; Because: (in order to prevent
  6872                              <1> 		       ; creating a dir with existing file name)
  6873                              <1> 		       ; Dir and file names must not be same!
  6874                              <1> 		       ; (return attribute must be checked)  	  	 	
  6875                              <1> sysfff_2:
  6876                              <1> 	; AX = Attributes mask 
  6877                              <1> 		; AL = AND mask (result must be equal to AL)
  6878                              <1> 		; AH = Negative AND mask (result must be ZERO)			
  6879                              <1>  	; ESI = FindFile_Name address
  6880                              <1> 
  6881 0000EE34 E8E69CFFFF          <1> 	call	find_first_file
  6882 0000EE39 72CC                <1> 	jc	short sysfff_err ; eax = 2 (File not found !)
  6883                              <1> 
  6884                              <1> 	; ESI = Directory Entry (FindFile_DirEntry) Location
  6885                              <1> 	; EDI = Directory Buffer Directory Entry Location
  6886                              <1> 	; EAX = File Size
  6887                              <1> 	;  BL = Attributes of The File/Directory
  6888                              <1> 	;  BH = Long Name Yes/No Status (>0 is YES)
  6889                              <1> 	;  DX > 0 : Ambiguous filename chars are used
  6890                              <1> 
  6891                              <1> sysfff_3:
  6892                              <1> 	; 16/10/2016
  6893 0000EE3B 668B0D[356B0100]    <1> 	mov	cx, [FFF_Attrib]
  6894                              <1> 	; Attribs in CL, return data type in CH
  6895                              <1> 
  6896                              <1> 	;or	cl, cl
  6897                              <1> 	;jz	short sysfff_4 ; 0 = No filter
  6898 0000EE42 80F1FF              <1> 	xor	cl, 0FFh
  6899 0000EE45 20D9                <1> 	and	cl, bl
  6900 0000EE47 7409                <1> 	jz	short sysfff_4
  6901                              <1> 
  6902                              <1> 	;mov	eax, 2 ; 'file not found !' error
  6903                              <1> 	;jmp	short sysfff_err_1
  6904                              <1> 
  6905                              <1> 	; 16/10/2016
  6906 0000EE49 E8809DFFFF          <1> 	call	find_next_file
  6907 0000EE4E 72B7                <1> 	jc	short sysfff_err ; eax = 12 (no more files !)
  6908 0000EE50 EBE9                <1> 	jmp	short sysfff_3
  6909                              <1> 
  6910                              <1> sysfff_4:
  6911 0000EE52 20ED                <1> 	and	ch, ch ; [FFF_RType]
  6912 0000EE54 7412                <1> 	jz	short sysfff_5
  6913 0000EE56 B980000000          <1> 	mov	ecx, 128 ; ; transfer length
  6914 0000EE5B 880D[346B0100]      <1> 	mov	[FFF_Valid], cl
  6915                              <1> sysfnf_11:
  6916 0000EE61 BE[E6670100]        <1> 	mov	esi, FindFile_Drv
  6917 0000EE66 EB44                <1> 	jmp	short sysfff_6	
  6918                              <1> sysfff_5:
  6919                              <1> 	;mov	esi, FindFile_DirEntry
  6920 0000EE68 B918000000          <1> 	mov	ecx, 24  ; transfer length
  6921 0000EE6D 880D[346B0100]      <1> 	mov	[FFF_Valid], cl
  6922                              <1> sysfnf_12:
  6923 0000EE73 BF[F06F0100]        <1> 	mov	edi, DTA ; FFF data transfer address
  6924                              <1> 	;mov	al, [esi+DirEntry_Attr] ; 11
  6925 0000EE78 88D8                <1> 	mov	al, bl ; File/Dir Attributes
  6926 0000EE7A 887F17              <1> 	mov	[edi+23], bh ; Longname length (0= none)
  6927 0000EE7D AA                  <1> 	stosb
  6928 0000EE7E 88D0                <1> 	mov	al, dl ; DL is for '?'
  6929 0000EE80 00F0                <1> 	add	al, dh ; DH is for '*'
  6930                              <1> 	; AL > 0 if ambiguous file name wildcards are used
  6931 0000EE82 AA                  <1> 	stosb
  6932 0000EE83 8B4616              <1> 	mov	eax, [esi+DirEntry_WrtTime] ; 22	
  6933 0000EE86 AB                  <1>         stosd	; DirEntry_WrtTime & DirEntry_WrtDate
  6934 0000EE87 8B461C              <1>         mov	eax, [esi+DirEntry_FileSize] ; 28
  6935 0000EE8A AB                  <1>         stosd
  6936 0000EE8B 668B4614            <1> 	mov	ax, [esi+DirEntry_FstClusHI] ; 20
  6937 0000EE8F 66C1E010            <1> 	shl	ax, 16
  6938 0000EE93 668B461A            <1> 	mov	ax, [esi+DirEntry_FstClusLO] ; 26 
  6939 0000EE97 A3[64030300]        <1> 	mov	[u.r0], eax ; First Cluster
  6940                              <1> 
  6941                              <1>         ;mov	esi, FindFile_DirEntry
  6942 0000EE9C E855140000          <1> 	call	get_file_name
  6943                              <1> 
  6944 0000EEA1 8A0D[346B0100]      <1> 	mov	cl, [FFF_Valid]
  6945 0000EEA7 BE[F06F0100]        <1>        	mov	esi, DTA ; FFF data transfer address
  6946                              <1> sysfff_6:
  6947 0000EEAC 8B3D[306B0100]      <1> 	mov	edi, [FFF_UBuffer] ; user's buffer address (edx)
  6948 0000EEB2 E8ABFEFFFF          <1> 	call	transfer_to_user_buffer
  6949                              <1> 
  6950 0000EEB7 890D[64030300]      <1> 	mov	[u.r0], ecx ; actual transfer count
  6951 0000EEBD E8F7130000          <1>         call 	reset_working_path
  6952 0000EEC2 E9D3E0FFFF          <1> 	jmp	sysret
  6953                              <1> 
  6954                              <1> sysfnf: ; <Find Next File>
  6955                              <1> 	; 16/10/2016 TRDOS 386 (TRDOS v2.0) feature only ! 
  6956                              <1> 	;           -derived from TRDOS v1.0, INT_21H.ASM-
  6957                              <1> 	;            ("loc_INT21h_find_next_file")
  6958                              <1> 	; TRDOS 8086 (v1.0)
  6959                              <1>         ; 	07/08/2011 
  6960                              <1>         ;	Find First File
  6961                              <1> 	;	INPUT:
  6962                              <1>         ;	    none
  6963                              <1> 	;	MSDOS OUTPUT:
  6964                              <1> 	;	    DTA: (Default address: PSP offset 80h)
  6965                              <1> 	;	    Offset  Descrription
  6966                              <1> 	;	    0	    Reserved for use find next file
  6967                              <1> 	;	    21	    Attribute of file found
  6968                              <1> 	;	    22	    Time stamp of file
  6969                              <1> 	;	    24	    Date stamp of file
  6970                              <1> 	;	    26	    File size in bytes
  6971                              <1> 	;	    30	    Filename and extension (zero terminated)
  6972                              <1> 	;	If cf = 1:
  6973                              <1> 	;	    Error Codes: (in AX)
  6974                              <1> 	;	       18 - No more files  			
  6975                              <1>         ;
  6976                              <1> 	; TRDOS 386 (v2.0) 
  6977                              <1> 	; 16/10/2016
  6978                              <1> 	;	
  6979                              <1>         ; INPUT ->
  6980                              <1>        	; 	   none
  6981                              <1> 	; OUTPUT ->
  6982                              <1> 	;	   EAX = 0 if CH input of 'Find First File' > 0
  6983                              <1> 	;	   EAX = First cluster number of file
  6984                              <1> 	;		 if CH input of 'Find First File' = 0	
  6985                              <1> 	;	   EDX = File parameters table/structure address
  6986                              <1> 	;
  6987                              <1> 	;          cf = 1 -> Error code in AL
  6988                              <1> 	;
  6989                              <1>  	; Modified Registers: EAX (at the return of system call)	
  6990                              <1> 
  6991                              <1> 	;	
  6992                              <1> 	; Note: If byte [FFF_Valid] = 0
  6993                              <1> 	;	'sysfnf' will return with 'no more files' error.
  6994                              <1> 	;	If byte [FFF_Valid] = 24
  6995                              <1> 	;	'sysfnf' will return with 32 bytes basic parameters
  6996                              <1> 	;	at the address which is in EDX.
  6997                              <1> 	;	If byte [FFF_Valid] = 128
  6998                              <1> 	;	'sysfnf' will return with 128 bytes Find File 
  6999                              <1> 	;	Structure/Table at the address which is in EDX.
  7000                              <1> 	
  7001 0000EEC7 803D[346B0100]00    <1> 	cmp	byte [FFF_Valid], 0
  7002 0000EECE 7714                <1> 	ja	short stsfnf_0
  7003                              <1>  	; 'no more files !' error 
  7004 0000EED0 B80C000000          <1> 	mov	eax, ERR_NO_MORE_FILES ; 12
  7005 0000EED5 A3[64030300]        <1> 	mov	[u.r0], eax
  7006 0000EEDA A3[C8030300]        <1> 	mov	[u.error], eax
  7007 0000EEDF E996E0FFFF          <1> 	jmp	error
  7008                              <1> stsfnf_0:
  7009                              <1> 	;cmp	byte [FFF_Valid], 128
  7010                              <1> 	;je	short stsfnf_1
  7011                              <1> 	;cmp	byte [FFF_Valid], 24
  7012                              <1> 	;je	short stsfnf_1
  7013                              <1> 	;mov	[FFF_Valid], 24 ; Default
  7014                              <1> stsfnf_1:
  7015 0000EEE4 0FB61D[465F0100]    <1> 	movzx	ebx, byte [Current_Drv]
  7016 0000EEEB 66891D[3A6B0100]    <1> 	mov	[SWP_DRV], bx
  7017 0000EEF2 8A15[E6670100]      <1> 	mov	dl, [FindFile_Drv]
  7018 0000EEF8 38DA                <1> 	cmp	dl, bl
  7019 0000EEFA 750B                <1> 	jne	short stsfnf_2
  7020 0000EEFC 86FB                <1> 	xchg	bh, bl
  7021 0000EEFE BE00010900          <1> 	mov	esi, Logical_DOSDisks
  7022 0000EF03 01DE                <1> 	add	esi, ebx
  7023 0000EF05 EB0D                <1> 	jmp	short sysfnf_3
  7024                              <1> 
  7025                              <1> stsfnf_2:
  7026 0000EF07 FE05[3B6B0100]      <1> 	inc	byte [SWP_DRV_chg]
  7027                              <1> 
  7028 0000EF0D E86A88FFFF          <1> 	call	change_current_drive
  7029 0000EF12 7245                <1> 	jc	short sysfnf_err_1 ; read error ! 
  7030                              <1> 				   ; (do not stop, because
  7031                              <1> 				   ; we don't have a
  7032                              <1> 				   ; 'no more files'
  7033                              <1> 				   ; -file not found- error,	
  7034                              <1> 				   ; next sysfnf system call
  7035                              <1> 				   ; may solve the problem,
  7036                              <1> 				   ; after re-placing the disk)				
  7037                              <1> sysfnf_3:
  7038 0000EF14 A1[5C680100]        <1> 	mov	eax, [FindFile_DirCluster]
  7039 0000EF19 21C0                <1> 	and	eax, eax
  7040 0000EF1B 7550                <1> 	jnz	short sysfnf_6
  7041                              <1>         
  7042 0000EF1D 803D[455F0100]02    <1> 	cmp	byte [Current_FATType], 2
  7043 0000EF24 772C                <1> 	ja	short sysfnf_err_0 ; invalid, we neeed to stop !?
  7044 0000EF26 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
  7045 0000EF2D 7223                <1> 	jb	short sysfnf_err_0 ; invalid, we neeed to stop !?
  7046                              <1> 
  7047 0000EF2F 3805[6C660100]      <1> 	cmp	byte [DirBuff_ValidData], al ; 0
  7048 0000EF35 7608                <1> 	jna	short sysfnf_4 
  7049                              <1> 
  7050 0000EF37 3B05[71660100]      <1> 	cmp	eax, [DirBuff_Cluster] ; 0 ?
  7051 0000EF3D 745E                <1> 	je	short sysfnf_9
  7052                              <1> 
  7053                              <1> 	;cmp	byte [Current_Dir_Level], 0
  7054                              <1>         ;ja	short sysfnf_4  
  7055                              <1>         ;jna	short sysfnf_9 
  7056                              <1> 
  7057                              <1> sysfnf_4:
  7058 0000EF3F FE05[3B6B0100]      <1> 	inc	byte [SWP_DRV_chg]
  7059 0000EF45 E815D6FFFF          <1> 	call 	load_FAT_root_directory
  7060 0000EF4A 7351                <1> 	jnc	short sysfnf_9
  7061                              <1> 	; eax = error code (17, 'drv not ready or read error')
  7062 0000EF4C EB0B                <1> 	jmp	short sysfnf_err_1 ; read error ! (no FNF stop)
  7063                              <1> 				   ; (if you want, try again, 
  7064                              <1> 				   ;  after re-placing the disk)
  7065                              <1> sysfnf_5:	
  7066 0000EF4E 3C0C                <1> 	cmp	al, 12 ; 'no more files' error
  7067 0000EF50 7507                <1> 	jne	short sysfnf_err_1 ; (no FNF stop -sysfnf will try
  7068                              <1> 				   ;  to read the directory again,
  7069                              <1> 				   ;  if the user calls sysfnf
  7070                              <1> 				   ;  just after this error return-)
  7071                              <1> 	; (FNF stop -sysfnf will not try
  7072                              <1> 	;  to read the directory again-)	
  7073                              <1> 
  7074                              <1> sysfnf_err_0:
  7075 0000EF52 C605[346B0100]00    <1> 	mov	byte [FFF_Valid], 0 ; FNF stop sign
  7076                              <1> sysfnf_err_1:
  7077 0000EF59 A3[64030300]        <1> 	mov	[u.r0], eax
  7078 0000EF5E A3[C8030300]        <1> 	mov	[u.error], eax
  7079 0000EF63 E851130000          <1> 	call	reset_working_path
  7080 0000EF68 E90DE0FFFF          <1> 	jmp	error
  7081                              <1> 	  
  7082                              <1> sysfnf_6:
  7083 0000EF6D 803D[6C660100]00    <1> 	cmp	byte [DirBuff_ValidData], 0
  7084 0000EF74 7608                <1> 	jna	short sysfnf_7
  7085                              <1> 
  7086 0000EF76 3B05[71660100]      <1> 	cmp	eax, [DirBuff_Cluster]
  7087 0000EF7C 741F                <1> 	je	short sysfnf_9
  7088                              <1> 
  7089                              <1> sysfnf_7:
  7090 0000EF7E FE05[3B6B0100]      <1> 	inc	byte [SWP_DRV_chg]
  7091 0000EF84 803D[455F0100]01    <1> 	cmp	byte [Current_FATType], 1
  7092 0000EF8B 7309                <1> 	jnb	short sysfnf_8
  7093                              <1> 
  7094                              <1> 	; Singlix (TRFS) File System 
  7095                              <1> 	; (access via compatibility buffer)
  7096 0000EF8D E895D6FFFF          <1> 	call	load_FS_sub_directory
  7097 0000EF92 7309                <1> 	jnc	short sysfnf_9
  7098                              <1> 
  7099 0000EF94 EBC3                <1> 	jmp	short sysfnf_err_1 ; read error (no FNF stop)
  7100                              <1> 
  7101                              <1> sysfnf_8:
  7102 0000EF96 E84FD6FFFF          <1> 	call	load_FAT_sub_directory	 
  7103 0000EF9B 72BC                <1> 	jc	short sysfnf_err_1 ; read error (no FNF stop)
  7104                              <1> 
  7105                              <1> sysfnf_9:
  7106 0000EF9D E82C9CFFFF          <1> 	call	find_next_file
  7107 0000EFA2 72AA                <1> 	jc	short sysfnf_5
  7108                              <1> 
  7109 0000EFA4 A0[356B0100]        <1> 	mov	al, [FFF_Attrib]
  7110                              <1> 	;or	al, al
  7111                              <1> 	;jz	short sysfnf_10 ; 0 = No filter
  7112 0000EFA9 34FF                <1> 	xor	al, 0FFh
  7113 0000EFAB 20D8                <1> 	and	al, bl
  7114 0000EFAD 75EE                <1> 	jnz	short sysfnf_9 ; search for next file until
  7115                              <1> 			       ; an error return from
  7116                              <1> 			       ; find_next_file procedure	
  7117                              <1> sysfnf_10:
  7118 0000EFAF 0FB60D[346B0100]    <1>         movzx	ecx, byte [FFF_Valid]
  7119 0000EFB6 80F980              <1> 	cmp	cl, 128 ; complete FindFile structure/table 
  7120 0000EFB9 0F84A2FEFFFF        <1> 	je	sysfnf_11
  7121                              <1> 	;cmp	cl, 24  ; basic parameters
  7122                              <1> 	;je	sysfnf_12       
  7123 0000EFBF E9AFFEFFFF          <1> 	jmp	sysfnf_12
  7124                              <1> 
  7125                              <1> writei:
  7126                              <1> 	; 26/10/2016
  7127                              <1> 	; 25/10/2016
  7128                              <1> 	; 23/10/2016
  7129                              <1> 	; 22/10/2016
  7130                              <1> 	; 19/10/2016 - TRDOS 386 (TRDOS v2.0)
  7131                              <1> 	; 19/05/2015 - 20/05/2015 (Retro UNIX 386 v1)
  7132                              <1> 	; 12/03/2013 - 31/07/2013 (Retro UNIX 8086 v1)
  7133                              <1> 	;
  7134                              <1> 	; Write data to file with first cluster number in EAX
  7135                              <1> 	; 
  7136                              <1> 	; INPUTS ->
  7137                              <1> 	;    EAX - First cluster number of the file
  7138                              <1> 	;    EBX - File number (Open file index number)
  7139                              <1> 	;    u.count - byte count to be written
  7140                              <1> 	;    u.base - points to user buffer
  7141                              <1> 	;    u.fofp - points to dword with current file offset
  7142                              <1> 	;    i.size - file size
  7143                              <1> 	;    cdev - logical dos drive number of the file
  7144                              <1> 	; OUTPUTS ->
  7145                              <1> 	;    u.count - cleared
  7146                              <1> 	;    u.nread - accumulates total bytes passed back
  7147                              <1> 	;    i.size - new file size (if file byte offset overs file size)
  7148                              <1> 	;    u.fofp - points to u.off (with new offset value)	
  7149                              <1> 	;
  7150                              <1> 	; (Retro UNIX Prototype : 11/11/2012 - 18/11/2012, UNIXCOPY.ASM)
  7151                              <1> 	; ((Modified registers: eax, edx, ebx, ecx, esi, edi, ebp)) 	
  7152                              <1> 
  7153 0000EFC4 31C9                <1> 	xor	ecx, ecx
  7154 0000EFC6 890D[8C030300]      <1> 	mov 	[u.nread], ecx  ; 0
  7155 0000EFCC 66890D[C4030300]    <1> 	mov	[u.pcount], cx ; 19/05/2015
  7156 0000EFD3 390D[88030300]      <1> 	cmp 	[u.count], ecx
  7157 0000EFD9 7701                <1> 	ja 	short writei_1 
  7158 0000EFDB C3                  <1> 	retn
  7159                              <1> writei_1:
  7160 0000EFDC 881D[F46A0100]      <1> 	mov	[writei.ofn], bl ; Open file number
  7161 0000EFE2 880D[2F6B0100]      <1> 	mov	[setfmod], cl ; 0 ; reset 'update lm date&time' sign
  7162                              <1> dskw_0: 
  7163                              <1> 	; 26/10/2016
  7164                              <1> 	; 22/10/2016, 23/10/2016, 25/10/2016
  7165                              <1> 	; 19/10/2016 - TRDOS 386 (TRDOS v2.0)
  7166                              <1> 	; 31/05/2015 - 25/07/2015 (Retro UNIX 386 v1)
  7167                              <1> 	; 26/04/2013 - 20/09/2013 (Retro UNIX 8086 v1)
  7168                              <1> 	;
  7169                              <1> 	; 01/08/2013 (mkdir_w check)
  7170 0000EFE8 E8D7000000          <1>  	call	mget_w
  7171                              <1> 	; eax = sector/block number
  7172                              <1> 
  7173 0000EFED 8B1D[74030300]      <1> 	mov     ebx, [u.fofp]
  7174 0000EFF3 8B13                <1> 	mov	edx, [ebx]
  7175 0000EFF5 81E2FF010000        <1> 	and	edx, 1FFh  ; / test the lower 9 bits of the file offset
  7176 0000EFFB 750C                <1> 	jnz	short dskw_1 ; / if its non-zero, branch
  7177                              <1> 			     ; if zero, file offset = 0,
  7178                              <1> 		       	     ; / 512, 1024,...(i.e., start of new block)
  7179 0000EFFD 813D[88030300]0002- <1> 	cmp	dword [u.count], 512
  7179 0000F005 0000                <1>
  7180                              <1> 				; / if zero, is there enough data to fill
  7181                              <1> 				; / an entire block? (i.e., no. of
  7182 0000F007 7337                <1> 	jnb	short dskw_2 ; / bytes to be written greater than 512.? 
  7183                              <1> 			     ; / Yes, branch. Don't have to read block
  7184                              <1> dskw_1: ; in as no past info. is to be saved 
  7185                              <1> 	; (the entire block will be overwritten).
  7186                              <1> 	; 23/10/2016
  7187                              <1> 
  7188 0000F009 BB[94070300]        <1> 	mov	ebx, writei_buffer
  7189                              <1> 	; esi = logical dos drive description table address
  7190                              <1> 	; eax = sector number
  7191                              <1> 	; ebx = buffer address (in kernel's memory space)
  7192                              <1> 	; ecx = sector count
  7193 0000F00E B901000000          <1> 	mov	ecx, 1
  7194 0000F013 E8A90D0000          <1> 	call	disk_read
  7195                              <1> 	;call	dskrd 	; / no, must retain old info.. 
  7196                              <1> 		       	; / Hence, read block 'r1' into an I/O buffer
  7197 0000F018 7326                <1> 	jnc	short dskw_2
  7198                              <1> 
  7199                              <1> 	; disk read error
  7200 0000F01A B811000000          <1> 	mov	eax, 17 ; drive not ready or READ ERROR !
  7201                              <1> dskw_err: ; jump from disk write error
  7202 0000F01F A3[64030300]        <1> 	mov	[u.r0], eax
  7203 0000F024 A3[C8030300]        <1> 	mov	[u.error], eax
  7204                              <1> 
  7205 0000F029 803D[2F6B0100]00    <1> 	cmp	byte [setfmod], 0
  7206 0000F030 0F8644DFFFFF        <1> 	jna	error
  7207                              <1> 
  7208 0000F036 E8AF030000          <1> 	call	update_file_lmdt ; update last modif. date&time of the file
  7209                              <1> 	;mov	byte [setfmod], 0	
  7210                              <1> 
  7211 0000F03B E93ADFFFFF          <1> 	jmp	error
  7212                              <1> 
  7213                              <1> dskw_2: ; 3:
  7214                              <1> 	; 23/10/2016
  7215 0000F040 C605[D06A0100]01    <1> 	mov	byte [writei.valid], 1 ; writei buffer contains valid data
  7216 0000F047 56                  <1> 	push	esi ; logical dos drive description table address
  7217                              <1> 	; EAX (r1) = block/sector number
  7218                              <1> 	;call	wslot
  7219                              <1> 		; jsr r0,wslot / set write and inhibit bits in I/O queue, 
  7220                              <1> 			   ; / proc. status=0, r5 points to 1st word of data
  7221 0000F048 803D[C6030300]00    <1> 	cmp	byte [u.kcall], 0
  7222 0000F04F 770F                <1> 	ja	short dskw_4 ; zf=0 -> the caller is 'mkdir'
  7223                              <1> 	;
  7224 0000F051 66833D[C4030300]00  <1> 	cmp	word [u.pcount], 0
  7225 0000F059 7705                <1> 	ja	short dskw_4
  7226                              <1> dskw_3:
  7227                              <1> 	; [u.base] = virtual address to transfer (as source address)
  7228 0000F05B E821FAFFFF          <1> 	call	trans_addr_r ; translate virtual address to physical (r)
  7229                              <1> dskw_4:
  7230 0000F060 BB[94070300]        <1> 	mov	ebx, writei_buffer
  7231                              <1> 	; EBX (r5) = system (I/O) buffer address
  7232 0000F065 E883FAFFFF          <1> 	call	sioreg
  7233                              <1> 	; ESI = file (user data) offset
  7234                              <1> 	; EDI = sector (I/O) buffer offset
  7235                              <1> 	; ECX = byte count
  7236                              <1> 	;
  7237 0000F06A F3A4                <1>   	rep	movsb
  7238                              <1> 	; 25/07/2015
  7239                              <1> 	; eax = remain bytes in buffer
  7240                              <1>         ;       (check if remain bytes in the buffer > [u.pcount])
  7241 0000F06C 09C0                <1> 	or	eax, eax
  7242 0000F06E 75EB                <1> 	jnz	short dskw_3 ; (page end before system buffer end!)	
  7243                              <1> 
  7244                              <1> 	; 23/10/2016
  7245 0000F070 B101                <1> 	mov	cl, 1
  7246 0000F072 5E                  <1> 	pop	esi
  7247 0000F073 A1[D46A0100]        <1> 	mov	eax, [writei.sector]
  7248                              <1> 	; esi = logical dos drive description table address
  7249                              <1> 	; eax = sector number
  7250                              <1> 	; ebx = writei buffer address
  7251                              <1> 	; ecx = sector count
  7252 0000F078 E8350D0000          <1> 	call	disk_write ; / yes, write the block
  7253 0000F07D 7307                <1> 	jnc	short dskw_5
  7254                              <1> 
  7255 0000F07F B812000000          <1> 	mov	eax, 18 ; drive not ready or WRITE ERROR !
  7256 0000F084 EB99                <1> 	jmp	short dskw_err
  7257                              <1> 
  7258                              <1> dskw_5:
  7259                              <1> 	; 26/10/2016
  7260 0000F086 0FB61D[F46A0100]    <1> 	movzx	ebx, byte [writei.ofn] ; open file number
  7261 0000F08D C0E302              <1> 	shl	bl, 2 ; *4
  7262 0000F090 8B83[C46E0100]      <1> 	mov	eax, [ebx+OF_POINTER]
  7263 0000F096 3B83[EC6E0100]      <1> 	cmp	eax, [ebx+OF_SIZE]
  7264 0000F09C 7606                <1> 	jna	short dskw_6
  7265 0000F09E 8983[EC6E0100]      <1> 	mov	[ebx+OF_SIZE], eax
  7266                              <1> dskw_6:
  7267                              <1> 	;shr	bl, 2
  7268 0000F0A4 833D[88030300]00    <1>         cmp     dword [u.count], 0 ; / any more data to write?
  7269 0000F0AB 760A                <1> 	jna	short dskw_7
  7270 0000F0AD A1[E46A0100]        <1> 	mov	eax, [writei.fclust]
  7271 0000F0B2 E931FFFFFF          <1> 	jmp	dskw_0 ; / yes, branch
  7272                              <1> dskw_7:
  7273                              <1>  	; update last modif. date&time of the file
  7274                              <1> 	; (also updates file size as OF_SIZE)
  7275 0000F0B7 E82E030000          <1> 	call	update_file_lmdt
  7276                              <1> 	;mov	byte [setfmod], 0	
  7277                              <1> 
  7278                              <1> 	; 03/08/2013
  7279 0000F0BC C605[C6030300]00    <1> 	mov	byte [u.kcall], 0
  7280                              <1> 	; 23/10/2016
  7281                              <1> 	;mov	eax, [writei.fclust]
  7282 0000F0C3 C3                  <1> 	retn
  7283                              <1> 
  7284                              <1> mget_w:
  7285                              <1> 	; 02/11/2016
  7286                              <1> 	; 01/11/2016
  7287                              <1> 	; 23/10/2016, 31/10/2016
  7288                              <1> 	; 22/10/2016 - TRDOS 386 (TRDOS v2.0)
  7289                              <1> 	; 03/06/2015 (Retro UNIX 386 v1, 'mget', u.5s)
  7290                              <1> 	; 22/03/2013 - 31/07/2013 (Retro UNIX 8086 v1)
  7291                              <1> 	;
  7292                              <1> 	; Get existing or (allocate) a new disk block for file
  7293                              <1> 	; 
  7294                              <1> 	; INPUTS ->
  7295                              <1> 	;    [u.fofp] = file offset pointer
  7296                              <1> 	;    [i.size] = file size
  7297                              <1> 	;    [u.count] = byte count	 
  7298                              <1> 	;    EAX = First cluster
  7299                              <1> 	;    [cdev] = Logical dos drive number 	  
  7300                              <1> 	;    [writei.ofn] = File Number
  7301                              <1> 	;		   (Open file index, 0 based)
  7302                              <1> 	;    ([u.off] = file offset)
  7303                              <1> 	; OUTPUTS ->
  7304                              <1> 	;    EAX = logical sector number
  7305                              <1> 	;    ESI = Logical Dos Drive Description Table address
  7306                              <1> 	;
  7307                              <1> 	; Modified registers: EDX, EBX, ECX, ESI, EDI, EBP  
  7308                              <1> 
  7309 0000F0C4 8B35[74030300]      <1>         mov     esi, [u.fofp]
  7310 0000F0CA 8B2E                <1> 	mov	ebp, [esi] ; u.off (or EBX*4+OF_POINTER)
  7311                              <1> 
  7312 0000F0CC 29C9                <1> 	sub	ecx, ecx
  7313 0000F0CE 8A2D[46030300]      <1> 	mov	ch, [cdev]
  7314                              <1> 
  7315 0000F0D4 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  7316 0000F0D9 01CE                <1> 	add	esi, ecx
  7317                              <1> 
  7318                              <1> 	; 31/10/2016
  7319 0000F0DB 89C3                <1> 	mov	ebx, eax ; First Cluster or FDT address
  7320                              <1> 
  7321 0000F0DD 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  7322 0000F0E1 0F86DD010000        <1> 	jna	mget_w_14 ; Singlix FS
  7323                              <1> 
  7324 0000F0E7 0FB74611            <1> 	movzx	eax, word [esi+LD_BPB+BytesPerSec]
  7325 0000F0EB 0FB65613            <1> 	movzx	edx, byte [esi+LD_BPB+SecPerClust]
  7326 0000F0EF 8815[D26A0100]      <1> 	mov	[writei.spc], dl  ; sectors per cluster
  7327 0000F0F5 F7E2                <1> 	mul	edx
  7328                              <1> 	; edx = 0
  7329                              <1> 	; eax = bytes per cluster (<= 65536)
  7330                              <1> 
  7331                              <1> 	; 02/11/2016
  7332 0000F0F7 89C1                <1> 	mov	ecx, eax
  7333 0000F0F9 48                  <1> 	dec	eax
  7334 0000F0FA 66A3[D86A0100]      <1> 	mov	[writei.bpc], ax	
  7335                              <1> 	
  7336 0000F100 89E8                <1> 	mov	eax, ebp
  7337 0000F102 0305[88030300]      <1> 	add	eax, [u.count] ; next file position
  7338 0000F108 3B05[55040300]      <1> 	cmp	eax, [i.size] ; <= file size ?
  7339 0000F10E 0F86FC000000        <1> 	jna	mget_w_4 ; no
  7340                              <1> 
  7341 0000F114 F7F1                <1> 	div	ecx
  7342 0000F116 A3[E06A0100]        <1> 	mov	[writei.c_index], eax ; cluster index
  7343                              <1> 	; edx = byte offset in cluster (<= 65535)
  7344                              <1> 	;mov	[writei.offset], dx
  7345                              <1> 	;shr	dx, 9 ; / 512
  7346                              <1> 	;mov	[writei.s_index], dl ; sector index in cluster (0 to spc -1)
  7347                              <1> 
  7348 0000F11B 29D2                <1> 	sub	edx, edx ; 01/11/2016
  7349 0000F11D 8915[D46A0100]      <1> 	mov 	[writei.sector], edx ; 0
  7350 0000F123 668915[DA6A0100]    <1> 	mov	[writei.offset], dx  ; byte offset in cluster 
  7351 0000F12A 8815[D36A0100]      <1> 	mov	[writei.s_index], dl ; sector index in cluster (0 to spc -1)
  7352                              <1> 
  7353 0000F130 89D8                <1> 	mov	eax, ebx ; First Cluster
  7354                              <1> 
  7355                              <1> 	; is this the 1st mget_w or a next mget_w call ? (by 'writei')
  7356 0000F132 3815[D06A0100]      <1> 	cmp	byte [writei.valid], dl ; 0 
  7357 0000F138 7624                <1> 	jna	short mget_w_0
  7358                              <1> 
  7359 0000F13A 8815[D06A0100]      <1> 	mov 	byte [writei.valid], dl ; 0 ; reset ('writei' will set it) 
  7360                              <1> 
  7361 0000F140 3B05[E46A0100]      <1> 	cmp	eax, [writei.fclust]
  7362 0000F146 7516                <1> 	jne	short mget_w_0
  7363                              <1> 
  7364 0000F148 8A0D[46030300]      <1> 	mov	cl, [cdev]
  7365 0000F14E 3A0D[D16A0100]      <1> 	cmp	cl, [writei.drv]
  7366 0000F154 7508                <1> 	jne	short mget_w_0
  7367                              <1>  	; [writei.l_clust] & [writei.l_index] are valid, 
  7368                              <1> 	;  we don't need to get last cluster & last cluster index
  7369 0000F156 8B0D[F06A0100]      <1> 	mov	ecx, [writei.l_index]
  7370 0000F15C EB64                <1> 	jmp	short mget_w_2
  7371                              <1> mget_w_0:
  7372 0000F15E A3[E46A0100]        <1> 	mov	[writei.fclust], eax ; first cluster
  7373                              <1> 	; edx = 0
  7374 0000F163 A3[DC6A0100]        <1> 	mov	[writei.cluster], eax ; first cluster ; 01/11/2016
  7375 0000F168 8915[E86A0100]      <1> 	mov 	[writei.fs_index], edx ; 0 ; curret cluster index
  7376                              <1> 
  7377                              <1> 	; FAT file system (FAT12, FAT16, FAT32)
  7378 0000F16E E88CDAFFFF          <1> 	call	get_last_cluster
  7379 0000F173 0F822B010000        <1> 	jc	mget_w_err ; eax = error code
  7380                              <1> 		
  7381 0000F179 A3[EC6A0100]        <1> 	mov	[writei.lclust], eax ; last cluster
  7382                              <1> 
  7383 0000F17E 8B0D[10690100]      <1> 	mov	ecx, [glc_index] ; last cluster index
  7384 0000F184 890D[F06A0100]      <1> 	mov	[writei.l_index], ecx
  7385                              <1> 
  7386 0000F18A A0[F46A0100]        <1> 	mov	al, [writei.ofn]
  7387 0000F18F FEC0                <1> 	inc	al
  7388 0000F191 A2[2F6B0100]        <1> 	mov	[setfmod], al ; update lm date&time sign
  7389                              <1> 
  7390                              <1> mget_w_1:
  7391 0000F196 3B0D[E06A0100]      <1> 	cmp	ecx, [writei.c_index]  ; last cluster index
  7392 0000F19C 7324                <1> 	jnb	short mget_w_2 ; 01/11/2016
  7393                              <1> 
  7394 0000F19E A1[EC6A0100]        <1> 	mov	eax, [writei.lclust]
  7395                              <1> 	; EAX = Last cluster
  7396 0000F1A3 E865DBFFFF          <1> 	call	add_new_cluster
  7397 0000F1A8 0F82F6000000        <1> 	jc	mget_w_err ; eax = error code
  7398                              <1> 	; edx = 0
  7399 0000F1AE A3[EC6A0100]        <1> 	mov	[writei.lclust], eax ; (new) last cluster
  7400 0000F1B3 8B0D[F06A0100]      <1> 	mov	ecx, [writei.l_index]
  7401 0000F1B9 41                  <1> 	inc	ecx ; add 1 to last cluster index
  7402 0000F1BA 890D[F06A0100]      <1> 	mov	[writei.l_index], ecx ; current last cluster index
  7403                              <1> 
  7404 0000F1C0 EBD4                <1> 	jmp	short mget_w_1
  7405                              <1> 
  7406                              <1> mget_w_2:
  7407 0000F1C2 89E9                <1> 	mov	ecx, ebp
  7408 0000F1C4 030D[88030300]      <1> 	add	ecx, [u.count]
  7409 0000F1CA 890D[55040300]      <1> 	mov	[i.size], ecx ; save new file size
  7410                              <1> 	;sub	edx, edx ; 0
  7411                              <1> 
  7412 0000F1D0 A0[46030300]        <1> 	mov	al, [cdev]
  7413 0000F1D5 A2[D16A0100]        <1> 	mov	[writei.drv], al ; physical drive number
  7414                              <1> 	; edx = 0
  7415 0000F1DA 89E8                <1> 	mov	eax, ebp ; file offset
  7416 0000F1DC 0FB70D[D86A0100]    <1> 	movzx	ecx, word [writei.bpc] ; bytes per cluster - 1
  7417 0000F1E3 41                  <1> 	inc	ecx ; bytes per cluster
  7418 0000F1E4 F7F1                <1> 	div	ecx
  7419                              <1> 	; edx = byte offset in cluster (<= 65535)
  7420                              <1> 	; eax = cluster index
  7421 0000F1E6 A3[E06A0100]        <1> 	mov	[writei.c_index], eax
  7422 0000F1EB 668915[DA6A0100]    <1> 	mov	[writei.offset], dx
  7423 0000F1F2 66C1EA09            <1> 	shr	dx, 9 ; / 512
  7424 0000F1F6 8815[D36A0100]      <1> 	mov	[writei.s_index], dl ; sector index in cluster (0 to spc -1)
  7425                              <1> 
  7426                              <1> mget_w_3:
  7427 0000F1FC 3B05[F06A0100]      <1> 	cmp	eax, [writei.l_index] ; last cluster index
  7428 0000F202 752A                <1> 	jne	short mget_w_5
  7429                              <1> 
  7430 0000F204 A3[E86A0100]        <1> 	mov	[writei.fs_index], eax ; cluster index (for next check)
  7431 0000F209 A1[EC6A0100]        <1> 	mov	eax, [writei.lclust] ; last cluster
  7432 0000F20E EB60                <1> 	jmp	short mget_w_10
  7433                              <1> 
  7434                              <1> mget_w_4: ; 02/11/2016
  7435                              <1> 	; eax = next file position
  7436 0000F210 2B05[88030300]      <1> 	sub	eax, [u.count] ; current file position
  7437                              <1> 	; edx = 0
  7438                              <1> 	; ecx = bytes per cluster
  7439 0000F216 F7F1                <1> 	div	ecx
  7440 0000F218 A3[E06A0100]        <1> 	mov	[writei.c_index], eax ; cluster index
  7441 0000F21D 668915[DA6A0100]    <1> 	mov	[writei.offset], dx
  7442 0000F224 66C1EA09            <1> 	shr	dx, 9 ; / 512
  7443 0000F228 8815[D36A0100]      <1> 	mov	[writei.s_index], dl ; sector index in cluster (0 to spc -1)
  7444                              <1> 
  7445                              <1> mget_w_5:
  7446 0000F22E 21C0                <1> 	and	eax, eax ; 0 = First Cluster's index number
  7447 0000F230 750C                <1> 	jnz	short mget_w_6
  7448                              <1> 
  7449 0000F232 A3[E86A0100]        <1> 	mov	[writei.fs_index], eax ; cluster index (for next check)
  7450 0000F237 A1[E46A0100]        <1> 	mov	eax, [writei.fclust] ; first cluster
  7451 0000F23C EB32                <1> 	jmp	short mget_w_10
  7452                              <1> 
  7453                              <1> mget_w_6:
  7454 0000F23E 3B05[E86A0100]      <1> 	cmp	eax, [writei.fs_index] ; current cluster index (>0)
  7455 0000F244 7507                <1> 	jne	short mget_w_7
  7456 0000F246 A1[DC6A0100]        <1> 	mov	eax, [writei.cluster] ; current cluster 
  7457 0000F24B EB3A                <1> 	jmp	short mget_w_11
  7458                              <1> 
  7459                              <1> mget_w_7:
  7460 0000F24D 89C1                <1> 	mov	ecx, eax
  7461 0000F24F 2B0D[E86A0100]      <1> 	sub	ecx, [writei.fs_index]
  7462 0000F255 730D                <1> 	jnc	short mget_w_8
  7463                              <1> 	; get cluster by index from the first cluster
  7464 0000F257 A1[E46A0100]        <1> 	mov	eax, [writei.fclust]
  7465 0000F25C 8B0D[E06A0100]      <1> 	mov	ecx, [writei.c_index]
  7466 0000F262 EB05                <1> 	jmp	short mget_w_9
  7467                              <1> 
  7468                              <1> mget_w_8:
  7469 0000F264 A1[DC6A0100]        <1> 	mov	eax, [writei.cluster] ; beginning cluster
  7470                              <1> 	; ecx = cluster sequence number after the beginning cluster
  7471                              <1> 	; sub	edx, edx ; 0
  7472                              <1> 
  7473                              <1> mget_w_9:
  7474                              <1> 	; EAX = Beginning cluster
  7475                              <1> 	; EDX = Sector index in disk/file section
  7476                              <1> 	;	(Only for SINGLIX file system!)
  7477                              <1> 	; ECX = Cluster sequence number after the beginning cluster
  7478                              <1> 	; ESI = Logical DOS Drive Description Table address
  7479 0000F269 E8A5DBFFFF          <1> 	call	get_cluster_by_index
  7480 0000F26E 7234                <1> 	jc	short mget_w_err ; error code in EAX
  7481                              <1> 	; EAX = Cluster number		
  7482                              <1> mget_w_10:
  7483 0000F270 A3[DC6A0100]        <1> 	mov	[writei.cluster], eax ; FDT number for Singlix File System
  7484                              <1> 
  7485 0000F275 807E0300            <1> 	cmp	byte [esi+LD_FATType], 0
  7486 0000F279 7638                <1> 	jna	short mget_w_13
  7487                              <1> 	; 01/11/2016
  7488 0000F27B 8B15[E06A0100]      <1> 	mov	edx, [writei.c_index]
  7489 0000F281 8915[E86A0100]      <1> 	mov	[writei.fs_index], edx
  7490                              <1> mget_w_11:
  7491 0000F287 83E802              <1> 	sub	eax, 2
  7492 0000F28A 0FB615[D26A0100]    <1> 	movzx	edx, byte [writei.spc]
  7493 0000F291 F7E2                <1> 	mul	edx
  7494                              <1> 
  7495 0000F293 034668              <1> 	add	eax, [esi+LD_DATABegin]
  7496 0000F296 8A15[D36A0100]      <1> 	mov	dl, [writei.s_index]
  7497 0000F29C 01D0                <1> 	add	eax, edx
  7498                              <1> mget_w_12:
  7499 0000F29E A3[D46A0100]        <1> 	mov	[writei.sector], eax
  7500                              <1> 	;; buffer validation must be done in writei
  7501                              <1> 	;;mov	byte [writei.valid], 1 
  7502 0000F2A3 C3                  <1> 	retn
  7503                              <1> 
  7504                              <1> mget_w_err:
  7505 0000F2A4 A3[C8030300]        <1> 	mov	[u.error], eax
  7506 0000F2A9 A3[64030300]        <1> 	mov	[u.r0], eax
  7507 0000F2AE E9C7DCFFFF          <1> 	jmp	error
  7508                              <1> 
  7509                              <1> mget_w_13:
  7510                              <1> 	; EAX = FDT number (Current Section)
  7511                              <1> 	; EDX = Sector index from the first section (0,1,2,3,4...)
  7512 0000F2B3 2B15[E86A0100]      <1> 	sub	edx, [writei.fs_index]	
  7513                              <1> 	; EDX = Sector index from current section
  7514 0000F2B9 8915[E86A0100]      <1> 	mov	[writei.fs_index], edx
  7515 0000F2BF 40                  <1> 	inc	eax ; the first data sector in FS disk section	
  7516 0000F2C0 01D0                <1> 	add	eax, edx
  7517 0000F2C2 EBDA                <1> 	jmp	short mget_w_12
  7518                              <1> 
  7519                              <1> mget_w_14:
  7520 0000F2C4 8A4E12              <1> 	mov	cl, [esi+LD_FS_BytesPerSec+1]
  7521 0000F2C7 D0E9                <1> 	shr	cl, 1 ;  ; 1 for 512 bytes, 4 for 2048 bytes
  7522 0000F2C9 880D[D26A0100]      <1> 	mov	[writei.spc], cl  ; sectors per cluster
  7523                              <1> 	; NOTE: writei bytes per sector value is always 512 ! 
  7524 0000F2CF 66C705[D86A0100]00- <1> 	mov	word [writei.bpc], 512
  7524 0000F2D7 02                  <1>
  7525                              <1> 
  7526 0000F2D8 89E9                <1> 	mov	ecx, ebp
  7527 0000F2DA 030D[88030300]      <1> 	add	ecx, [u.count] ; next file position
  7528 0000F2E0 3B0D[55040300]      <1> 	cmp	ecx, [i.size] ; <= file size ?
  7529 0000F2E6 0F86C8000000        <1> 	jna	mget_w_19 ; no
  7530                              <1> 
  7531 0000F2EC 29D2                <1> 	sub	edx, edx ; 0
  7532 0000F2EE 8915[D46A0100]      <1> 	mov 	[writei.sector], edx ; 0
  7533 0000F2F4 668915[DA6A0100]    <1> 	mov	[writei.offset], dx  ; byte offset in cluster 
  7534 0000F2FB 8815[D36A0100]      <1> 	mov	[writei.s_index], dl ; sector index in cluster (0 to spc -1)
  7535                              <1> 
  7536 0000F301 C1E909              <1> 	shr	ecx, 9 ; 1 cluster = 512 bytes
  7537 0000F304 890D[E06A0100]      <1> 	mov	[writei.c_index], ecx ; section/cluster index
  7538                              <1> 	
  7539 0000F30A 89D8                <1> 	mov	eax, ebx ; FDT number (First FDT address)
  7540                              <1> 
  7541                              <1> 	; is this the 1st mget_w or a next mget_w call ? (by 'writei')
  7542 0000F30C 3815[D06A0100]      <1> 	cmp	byte [writei.valid], dl ; 0 
  7543 0000F312 7624                <1> 	jna	short mget_w_15
  7544                              <1> 
  7545 0000F314 8815[D06A0100]      <1> 	mov 	byte [writei.valid], dl ; 0 ; reset ('writei' will set it) 
  7546                              <1> 
  7547 0000F31A 3B05[E46A0100]      <1> 	cmp	eax, [writei.fclust]
  7548 0000F320 7516                <1> 	jne	short mget_w_15
  7549                              <1> 
  7550 0000F322 8A0D[46030300]      <1> 	mov	cl, [cdev]
  7551 0000F328 3A0D[D16A0100]      <1> 	cmp	cl, [writei.drv]
  7552 0000F32E 7508                <1> 	jne	short mget_w_15
  7553                              <1>  	; [writei.l_clust] & [writei.l_index] are valid, 
  7554                              <1> 	;  we don't need to get last cluster & last cluster index
  7555 0000F330 8B0D[F06A0100]      <1> 	mov	ecx, [writei.l_index]
  7556 0000F336 EB49                <1> 	jmp	short mget_w_17
  7557                              <1> mget_w_15:
  7558 0000F338 A3[E46A0100]        <1> 	mov	[writei.fclust], eax ; first section (FDT number)
  7559                              <1> 	; edx = 0
  7560 0000F33D 8915[DC6A0100]      <1> 	mov	[writei.cluster], edx ; 0 ; current section
  7561 0000F343 8915[E86A0100]      <1> 	mov 	[writei.fs_index], edx ; 0 ; curret section index
  7562                              <1> 
  7563                              <1> 	; eax = FDT number (section 0 header address)
  7564 0000F349 E8EFDAFFFF          <1> 	call	get_last_section
  7565 0000F34E 0F8250FFFFFF        <1> 	jc	mget_w_err ; eax = error code
  7566                              <1> 
  7567 0000F354 8915[E86A0100]      <1> 	mov 	[writei.fs_index], edx ; sector index in last section
  7568                              <1> 		
  7569 0000F35A A3[EC6A0100]        <1> 	mov	[writei.lclust], eax ; last section address
  7570                              <1> 
  7571 0000F35F 8B0D[10690100]      <1> 	mov	ecx, [glc_index] ; last section index
  7572 0000F365 890D[F06A0100]      <1> 	mov	[writei.l_index], ecx
  7573                              <1> 
  7574 0000F36B A0[F46A0100]        <1> 	mov	al, [writei.ofn]
  7575 0000F370 FEC0                <1> 	inc	al
  7576 0000F372 A2[2F6B0100]        <1> 	mov	[setfmod], al ; update lm date&time sign
  7577                              <1> 
  7578                              <1> mget_w_16:
  7579                              <1> 	; edx = (existing) last section (sector) index
  7580 0000F377 8B0D[E06A0100]      <1> 	mov	ecx, [writei.c_index] ; final section (sector) index
  7581 0000F37D 29D1                <1> 	sub	ecx, edx
  7582 0000F37F 7633                <1> 	jna	short mget_w_19
  7583                              <1> 	 ; ecx = sector count
  7584                              <1> mget_w_17:
  7585 0000F381 A1[EC6A0100]        <1> 	mov	eax, [writei.lclust]
  7586                              <1> 	; ESI = Logical dos drv desc. table address
  7587                              <1>         ; EAX = Last section
  7588                              <1>         ; (ECX = 0 for directory) 
  7589                              <1>         ; ECX = sector count (except FDT)
  7590 0000F386 E875D0FFFF          <1> 	call	add_new_fs_section
  7591 0000F38B 7312                <1> 	jnc	short mget_w_18
  7592                              <1> 
  7593                              <1> 	; If error number = 27h (insufficient disk space)
  7594                              <1> 	; it is needed to check free consequent sectors
  7595                              <1> 	; (1 data sector at least and +1 section header sector) 
  7596                              <1> 
  7597 0000F38D 83F827              <1> 	cmp	eax, 27h
  7598 0000F390 0F850EFFFFFF        <1> 	jne	mget_w_err ; eax = error code
  7599                              <1> 
  7600                              <1> 	; ecx = count of free consequent sectors
  7601                              <1> 	; ecx must be > 1 (1 data + 1 header sector)
  7602 0000F396 49                  <1> 	dec	ecx
  7603 0000F397 0F8407FFFFFF        <1> 	jz	mget_w_err
  7604 0000F39D EBE2                <1> 	jmp	short mget_w_17
  7605                              <1> 
  7606                              <1> mget_w_18:
  7607 0000F39F A3[EC6A0100]        <1> 	mov	[writei.lclust], eax ; (new) last section
  7608                              <1> 	; ecx = sector count (except section header)
  7609 0000F3A4 8B15[F06A0100]      <1> 	mov	edx, [writei.l_index]
  7610 0000F3AA 01CA                <1> 	add	edx, ecx ; add sector count to index
  7611 0000F3AC 8915[F06A0100]      <1> 	mov	[writei.l_index], edx
  7612 0000F3B2 EBC3                <1> 	jmp	short mget_w_16
  7613                              <1> 
  7614                              <1> mget_w_19:
  7615 0000F3B4 89E9                <1> 	mov	ecx, ebp
  7616 0000F3B6 030D[88030300]      <1> 	add	ecx, [u.count]
  7617 0000F3BC 890D[55040300]      <1> 	mov	[i.size], ecx ; save new file size
  7618                              <1> 	;sub	edx, edx ; 0
  7619                              <1> 
  7620 0000F3C2 A0[46030300]        <1> 	mov	al, [cdev]
  7621 0000F3C7 A2[D16A0100]        <1> 	mov	[writei.drv], al ; physical drive number
  7622                              <1> 	; edx = 0
  7623 0000F3CC 89E8                <1> 	mov	eax, ebp ; file offset
  7624 0000F3CE 89C2                <1> 	mov	edx, eax
  7625                              <1> 	; 1 cluster = 512 bytes (for Singlix FS)
  7626 0000F3D0 C1E809              <1> 	shr	eax, 9  ; / 512
  7627 0000F3D3 81E2FF010000        <1> 	and	edx, 1FFh
  7628                              <1> 	; edx = byte offset in cluster/sector (<= 511)
  7629                              <1> 	; eax = section (sector/cluster) index
  7630 0000F3D9 A3[E06A0100]        <1> 	mov	[writei.c_index], eax
  7631 0000F3DE 668915[DA6A0100]    <1> 	mov	[writei.offset], dx
  7632                              <1> 	;mov	byte [writei.s_index], 0 ; sector index in cluster
  7633 0000F3E5 E912FEFFFF          <1> 	jmp	mget_w_3
  7634                              <1> 
  7635                              <1> update_file_lmdt: ; & update file size
  7636                              <1> 	; 26/10/2016
  7637                              <1> 	; 24/10/2016
  7638                              <1> 	; 23/10/2016
  7639                              <1> 	; 22/10/2016 - TRDOS 386 (TRDOS v2.0)
  7640                              <1> 	;
  7641                              <1> 	; Update last modification date&time of file
  7642                              <1> 	; (call from syswrite -> writei)
  7643                              <1> 	; ((also updates file size)) // 26/10/2016
  7644                              <1> 	; 
  7645                              <1> 	; INPUT:
  7646                              <1> 	;      byte [setfmod] = open file number
  7647                              <1> 	; OUTPUT:
  7648                              <1> 	;      cf = 0 -> success !
  7649                              <1> 	;      cf = 1 -> lmdt update has been failed! 	 
  7650                              <1> 	;
  7651                              <1> 	; Modified registers: eax, ebx, ecx, edx, esi, edi       				
  7652                              <1> 	;
  7653                              <1> 
  7654                              <1> 	;cmp	byte [setfmod], 0
  7655                              <1> 	;jna	short uflmdt_2 ; nothing to do
  7656                              <1> 
  7657 0000F3EA 31C0                <1> 	xor	eax, eax
  7658                              <1> 
  7659 0000F3EC 0FB61D[2F6B0100]    <1> 	movzx	ebx, byte [setfmod]
  7660 0000F3F3 FECB                <1> 	dec	bl ; open file index number (0 based)
  7661                              <1> 
  7662 0000F3F5 8AA3[9C6E0100]      <1> 	mov	ah, [ebx+OF_DRIVE]
  7663 0000F3FB BE00010900          <1> 	mov	esi, Logical_DOSDisks
  7664 0000F400 01C6                <1> 	add	esi, eax
  7665 0000F402 C0E302              <1> 	shl	bl, 2 ; *4	
  7666 0000F405 8B8B[746E0100]      <1> 	mov	ecx, [ebx+OF_FCLUSTER] ; first cluster
  7667 0000F40B 8B93[3C6F0100]      <1> 	mov	edx, [ebx+OF_DIRCLUSTER] ; dir cluster
  7668                              <1> 
  7669 0000F411 D0EB                <1> 	shr	bl, 1 ; /2
  7670 0000F413 0FB7BB[DC6F0100]    <1> 	movzx	edi, word [ebx+OF_DIRENTRY]
  7671                              <1> 	
  7672 0000F41A 803D[6C660100]01    <1> 	cmp	byte [DirBuff_ValidData], 1
  7673 0000F421 726E                <1> 	jb	short uflmdt_4
  7674                              <1> 
  7675 0000F423 A0[6A660100]        <1> 	mov	al, [DirBuff_DRV]
  7676 0000F428 2C41                <1> 	sub	al, 'A'	
  7677 0000F42A 38E0                <1> 	cmp	al, ah
  7678 0000F42C 7563                <1> 	jne	short uflmdt_4 ; different drive
  7679 0000F42E 8A4603              <1> 	mov	al, [esi+LD_FATType] 
  7680 0000F431 3A05[6B660100]      <1> 	cmp	al, [DirBuff_FATType]
  7681 0000F437 755B                <1> 	jne	short uflmdt_5 ; different FS type
  7682 0000F439 3B15[71660100]      <1> 	cmp	edx, [DirBuff_Cluster]
  7683 0000F43F 7553                <1> 	jne	short uflmdt_5 ; different cluster
  7684                              <1> 
  7685                              <1> uflmdt_1:
  7686                              <1> 	; Directory buffer is ready here!
  7687                              <1> 	; OF_FCLUSTER must be compared/verified
  7688 0000F441 BE00000800          <1> 	mov	esi, Directory_Buffer
  7689 0000F446 66C1E705            <1> 	shl	di, 5 ; dir entry index * 32
  7690 0000F44A 01FE                <1> 	add	esi, edi ; offset
  7691                              <1> 	;
  7692 0000F44C F6460B18            <1> 	test	byte [esi+DirEntry_Attr], 18h ; Vol & Dir
  7693 0000F450 750F                <1> 	jnz	short uflmdt_2 ; not a valid file !
  7694 0000F452 668B4614            <1> 	mov	ax, [esi+DirEntry_FstClusHI]
  7695 0000F456 C1E010              <1> 	shl	eax, 16
  7696 0000F459 668B461A            <1> 	mov	ax, [esi+DirEntry_FstClusLO]
  7697 0000F45D 39C8                <1> 	cmp	eax, ecx ; same first cluster ?
  7698 0000F45F 7407                <1> 	je	short uflmdt_3 ; yes, it is OK !!!	
  7699                              <1> 
  7700                              <1> uflmdt_2:	
  7701                              <1> 	; save directory buffer if has modified/changed sign
  7702                              <1> 	; (It is good to save dir buff even if the searched
  7703                              <1> 	; directory entry is not found !?)
  7704 0000F461 E8EEBCFFFF          <1> 	call	save_directory_buffer
  7705 0000F466 F9                  <1> 	stc	; update failed
  7706 0000F467 C3                  <1> 	retn
  7707                              <1> 	
  7708                              <1> uflmdt_3:
  7709                              <1> 	; Update directory entry
  7710                              <1> 	; 26/10/2016
  7711 0000F468 D0E3                <1> 	shl	bl, 1 ; *2 
  7712 0000F46A 8B83[EC6E0100]      <1> 	mov	eax, [ebx+OF_SIZE] ; file size
  7713 0000F470 89461C              <1> 	mov	[esi+DirEntry_FileSize], eax
  7714                              <1> 	;
  7715 0000F473 E83EBCFFFF          <1> 	call	convert_current_date_time
  7716                              <1> 	; OUTPUT -> DX = Date in dos dir entry format
  7717                              <1>         ; 	    AX = Time in dos dir entry format	
  7718 0000F478 66894616            <1> 	mov	[esi+DirEntry_WrtTime], ax
  7719 0000F47C 66895618            <1> 	mov	[esi+DirEntry_WrtDate], dx	
  7720 0000F480 66895612            <1> 	mov	[esi+DirEntry_LastAccDate], dx
  7721 0000F484 C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2
  7722 0000F48B E8C4BCFFFF          <1> 	call	save_directory_buffer
  7723 0000F490 C3                  <1> 	retn
  7724                              <1> 
  7725                              <1> uflmdt_4:
  7726                              <1> 	; Directory buffer sector read&write
  7727                              <1> 	; 23/10/2016
  7728                              <1> 	;
  7729 0000F491 8A4603              <1> 	mov	al, [esi+LD_FATType]
  7730                              <1> uflmdt_5:
  7731 0000F494 BB[9C090300]        <1> 	mov	ebx, rw_buffer ; Common r/w sector buffer addr
  7732                              <1> 		
  7733 0000F499 20C0                <1> 	and	al, al ; 0 = Singlix FS
  7734 0000F49B 0F8492000000        <1> 	jz	uflmdt_11
  7735                              <1> 
  7736 0000F4A1 21D2                <1> 	and	edx, edx
  7737 0000F4A3 7521                <1> 	jnz	short uflmdt_9
  7738                              <1> 
  7739 0000F4A5 3C02                <1> 	cmp	al, 2  ; 3 = FAT32
  7740 0000F4A7 771A                <1> 	ja	short uflmdt_8
  7741                              <1> 
  7742 0000F4A9 89F8                <1> 	mov	eax, edi ; directory entry index number
  7743 0000F4AB 66C1E804            <1> 	shr	ax, 4 ; 16 entries per sector	 
  7744 0000F4AF 034664              <1> 	add	eax, [esi+LD_ROOTBegin]
  7745                              <1> 	; eax = root directory sector
  7746                              <1> uflmdt_6:
  7747 0000F4B2 50                  <1> 	push	eax ; * ; disk sector address
  7748 0000F4B3 51                  <1> 	push	ecx ; first cluster	
  7749 0000F4B4 B901000000          <1> 	mov	ecx, 1
  7750                              <1> 	; ecx = sector count
  7751 0000F4B9 E803090000          <1> 	call	disk_read
  7752 0000F4BE 59                  <1> 	pop	ecx
  7753 0000F4BF 731A                <1> 	jnc	short uflmdt_10
  7754 0000F4C1 58                  <1> 	pop	eax ; *
  7755                              <1> uflmdt_7:
  7756 0000F4C2 C3                  <1> 	retn	
  7757                              <1> 
  7758                              <1> uflmdt_8:
  7759 0000F4C3 8B5632              <1> 	mov	edx, [esi+LD_BPB+FAT32_RootFClust]
  7760                              <1> uflmdt_9:
  7761 0000F4C6 83FA02              <1> 	cmp	edx, 2
  7762 0000F4C9 72F7                <1> 	jb	short uflmdt_7 ; invalid, nothing to do
  7763                              <1> 
  7764 0000F4CB 83EA02              <1> 	sub	edx, 2
  7765 0000F4CE 89D0                <1> 	mov	eax, edx
  7766 0000F4D0 0FB65613            <1> 	movzx	edx, byte [esi+LD_BPB+SecPerClust]
  7767 0000F4D4 F7E2                <1> 	mul	edx
  7768 0000F4D6 034668              <1> 	add	eax, [esi+LD_DATABegin]
  7769                              <1> 	; eax = sub directory (data) sector 
  7770 0000F4D9 EBD7                <1> 	jmp	short uflmdt_6
  7771                              <1> 
  7772                              <1> uflmdt_10:
  7773                              <1> 	; Directory sector buffer is ready here!
  7774                              <1> 	; OF_FCLUSTER must be compared/verified
  7775                              <1> 	; edi = dir entry index number (<= 2047)
  7776 0000F4DB 6683E70F            <1> 	and	di, 0Fh ; 16 entries per sector
  7777 0000F4DF 66C1E705            <1> 	shl	di, 5 ; dir entry index * 32
  7778 0000F4E3 81C7[9C090300]      <1> 	add	edi, rw_buffer
  7779                              <1> 	;
  7780 0000F4E9 F6470B18            <1> 	test	byte [edi+DirEntry_Attr], 18h ; Vol & Dir
  7781 0000F4ED 0F856EFFFFFF        <1> 	jnz	uflmdt_2 ; not a valid file !
  7782 0000F4F3 668B5714            <1> 	mov	dx, [edi+DirEntry_FstClusHI]
  7783 0000F4F7 C1E210              <1> 	shl	edx, 16
  7784 0000F4FA 668B571A            <1> 	mov	dx, [edi+DirEntry_FstClusLO]
  7785 0000F4FE 39CA                <1> 	cmp	edx, ecx ; same first cluster ?
  7786 0000F500 0F855BFFFFFF        <1> 	jne	uflmdt_2 ; no !?
  7787                              <1> 
  7788                              <1> 	; Update directory entry
  7789 0000F506 E8ABBBFFFF          <1> 	call	convert_current_date_time
  7790                              <1> 	; OUTPUT -> DX = Date in dos dir entry format
  7791                              <1>         ; 	    AX = Time in dos dir entry format	
  7792 0000F50B 66894716            <1> 	mov	[edi+DirEntry_WrtTime], ax
  7793 0000F50F 66895718            <1> 	mov	[edi+DirEntry_WrtDate], dx	
  7794 0000F513 66895712            <1> 	mov	[edi+DirEntry_LastAccDate], dx
  7795                              <1> 	
  7796 0000F517 58                  <1> 	pop	eax ; *
  7797                              <1> 
  7798 0000F518 BB[9C090300]        <1> 	mov	ebx, rw_buffer ; Common r/w sector buffer addr
  7799 0000F51D B901000000          <1> 	mov	ecx, 1
  7800                              <1> 	; esi = logical dos description table address
  7801                              <1> 	; eax = disk sector number/address (LBA)
  7802                              <1> 	; ecx = sector count
  7803                              <1> 	; ebx = buffer address
  7804 0000F522 E88B080000          <1> 	call	disk_write
  7805 0000F527 0F8234FFFFFF        <1> 	jc	uflmdt_2
  7806                              <1> 	
  7807                              <1> 	; save directory buffer if has modified/changed sign
  7808 0000F52D E822BCFFFF          <1> 	call	save_directory_buffer
  7809 0000F532 C3                  <1> 	retn
  7810                              <1> 
  7811                              <1> uflmdt_11:
  7812                              <1> 	; 24/10/2016
  7813                              <1> 	; Update last modification date & time of a file
  7814                              <1> 	; on a disk with Singlix File System.
  7815                              <1> 	;
  7816                              <1> 	; (Method: Read the FDT -File Description Table-
  7817                              <1> 	; sector of the file and update the lmdt data fields,
  7818                              <1> 	; then write FDT sector to the disk.
  7819                              <1> 	; /// It is easy but there is compatibility buffer
  7820                              <1> 	; method also for changing directory entry data and
  7821                              <1> 	; also there are some programming issues for Singlix
  7822                              <1> 	; file system (TRFS), which are not completed yet!)
  7823                              <1> 	;
  7824                              <1> 	; Not ready yet ! (24/10/2016)
  7825                              <1> 	; /// Temporary code for error return ! ///
  7826 0000F533 31C0                <1> 	xor	eax, eax
  7827 0000F535 F9                  <1> 	stc
  7828 0000F536 C3                  <1> 	retn
  7829                              <1> 
  7830                              <1> sysalloc:
  7831                              <1> 	; 14/10/2017
  7832                              <1> 	; 20/08/2017, 01/09/2017
  7833                              <1> 	; 20/02/2017, 04/03/2017, 15/05/2017
  7834                              <1> 	; 19/02/2017 - TRDOS 386 (TRDOS v2.0)
  7835                              <1> 	; (TRDOS 386 feature only!)
  7836                              <1> 	;
  7837                              <1> 	; Allocate Contiguous Memory Block/Pages (for user)
  7838                              <1> 	; (System call for DMA Buffer allocation etc.)	
  7839                              <1> 	;
  7840                              <1> 	; INPUT ->
  7841                              <1> 	;	EBX = Virtual address (for user)
  7842                              <1> 	;	     (Physical memory block/aperture
  7843                              <1> 	;	     will be mapped to this virtual address) 
  7844                              <1> 	;	ECX = Byte Count
  7845                              <1> 	;	     (will be rounded up to page border)
  7846                              <1> 	;	If ECX = 0
  7847                              <1> 	;	    System call will return with an error (cf=1)
  7848                              <1> 	;	    but ECX will contain maximum size of
  7849                              <1> 	;	    available memory aperture and physical
  7850                              <1> 	;	    (beginning) address of that aperture
  7851                              <1> 	;	    (which have maximum size) will be in EAX.
  7852                              <1> 	;	EDX = Upper limit of the requested physical memory
  7853                              <1> 	;	      block/pages.
  7854                              <1> 	;	     (The last byte address of the memory aperture 
  7855                              <1> 	;	      must not be equal to or above this limit.)	
  7856                              <1> 	;	If EDX = 0
  7857                              <1> 	; 	   there is NOLIMIT !
  7858                              <1> 	;	If EDX = 0FFFFFFFFh (-1) 
  7859                              <1> 	;	   ESI = Lower Limit !
  7860                              <1> 	;		(Beginning of the block must not be 'less'
  7861                              <1> 	;		than this.) (Must be equal to or above...)
  7862                              <1> 	;	   EDI = Upper Limit !
  7863                              <1> 	;		(End of the block must be !less! than this)
  7864                              <1> 	;		(The last byte addr of the memory aperture 
  7865                              <1> 	;		must not be equal to or above this limit.)
  7866                              <1> 	;
  7867                              <1> 	; OUTPUT ->
  7868                              <1> 	;	If CF = 0
  7869                              <1> 	;	EAX = Physical address of the allocated memory block
  7870                              <1> 	;	ECX = Allocated bytes (as rounded up to page borders)
  7871                              <1> 	;	EBX = Virtual address (as rounded up)
  7872                              <1> 	;	IF CF = 1
  7873                              <1> 	;	    Requested (size of) Memory block could not be 
  7874                              <1> 	;	    allocated to the user!	
  7875                              <1> 	;	IF CF = 1 & EAX = 0 (Insufficient memory error!)
  7876                              <1> 	;	   ECX = Total number of free bytes
  7877                              <1> 	;	         (not size of available contiguous bytes!)		 	
  7878                              <1> 	;	If CF = 1 & EAX > 0
  7879                              <1> 	;	   there is not a memory aperture with requested size
  7880                              <1> 	;	   but total free mem is not less than requested size.
  7881                              <1> 	;	   EAX = Physical addr of available memory aperture
  7882                              <1> 	;	   	 with max size 
  7883                              <1> 	;	        (but it doesn't fit to the conditions!) 	
  7884                              <1> 	;	   ECX = Size of available memory aperture in bytes.
  7885                              <1> 	;	If CF = 1 -> EAX = 0FFFFFFFFh	
  7886                              <1> 	;	   Conditions/Parameters are wrong !		 		
  7887                              <1> 	;	   ECX is same with input value.
  7888                              <1> 	;
  7889                              <1> 	; Note:	Previously allocated pages will be deallocated if
  7890                              <1> 	;       new allocation conditions are met.
  7891                              <1> 	;
  7892                              <1> 	; Note: u.break control may be included in future versions	
  7893                              <1> 	;
  7894                              <1> 
  7895 0000F537 31C0                <1> 	xor	eax, eax ; 0
  7896                              <1> 	; 14/10/2017
  7897 0000F539 4A                  <1> 	dec	edx ; is there a limit ?
  7898 0000F53A 7810                <1> 	js	short sysalloc_1 ;  0 -> 0FFFFFFFFh -> NO LIMIT
  7899 0000F53C 42                  <1> 	inc	edx ; > 0
  7900                              <1> 	; Check upper address limit
  7901                              <1> 	;(round up to page borders)
  7902 0000F53D 81C1FF0F0000        <1> 	add	ecx, PAGE_SIZE-1 ; 4095
  7903 0000F543 6681E100F0          <1> 	and	cx, ~PAGE_OFF ; not 4095
  7904 0000F548 39CA                <1> 	cmp	edx, ecx ; upper limit - block size
  7905 0000F54A 7224                <1> 	jb	short sysalloc_err
  7906                              <1> sysalloc_1:
  7907                              <1> 	; EAX = Beginning address (physical)
  7908                              <1> 	; EAX = 0 -> Allocate mem block from the 1st proper aperture	
  7909                              <1> 	; ECX = Number of bytes to be allocated		
  7910 0000F54C E83E66FFFF          <1> 	call	allocate_memory_block
  7911 0000F551 721D                <1> 	jc	short sysalloc_err
  7912                              <1> 	; 01/09/2017
  7913 0000F553 29C2                <1> 	sub	edx, eax ; upper limit address - beginning address
  7914 0000F555 760F                <1> 	jna	short sysalloc_3 ; begin addr not less than the limit
  7915 0000F557 39CA                <1> 	cmp	edx, ecx
  7916 0000F559 720B                <1> 	jb	short sysalloc_3 ; end address overs the limit
  7917                              <1> sysalloc_2:	
  7918                              <1> 	; EAX = Beginning (physical) addr of the allocated mem block
  7919                              <1> 	; ECX = Num of allocated bytes (rounded up to page borders) 
  7920 0000F55B 50                  <1> 	push	eax ; * ; 04/03/2017	
  7921                              <1> 	; Here, requested contiquous memory pages have been allocated
  7922                              <1> 	; on Memory Allocation Table but user's page directory 
  7923                              <1> 	; and page tables have not been updated yet!
  7924 0000F55C 51                  <1> 	push	ecx ; **
  7925                              <1> 	; ebx = virtual address (will be rounded up to page border)
  7926                              <1> 	; ecx = number of bytes to be deallocated
  7927                              <1> 	;	will be adjusted to ebx+ecx round down - ebx round up
  7928 0000F55D E88869FFFF          <1> 	call	deallocate_user_pages 
  7929 0000F562 731F                <1> 	jnc	short sysalloc_4 ; EAX = Deallocated memory bytes
  7930 0000F564 59                  <1> 	pop	ecx ; **
  7931 0000F565 58                  <1> 	pop	eax ; *
  7932                              <1> sysalloc_3:
  7933                              <1> 	; error !
  7934                              <1> 	; restore Memory Allocation Table Content
  7935 0000F566 E83168FFFF          <1> 	call	deallocate_memory_block
  7936 0000F56B 31C0                <1> 	xor	eax, eax ; 0
  7937 0000F56D 48                  <1> 	dec	eax ; 0FFFFFFFFh ; 15/05/2017
  7938 0000F56E EB09                <1> 	jmp	short sysalloc_wrong
  7939                              <1> sysalloc_err:
  7940 0000F570 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; ebp points to user's registers
  7941 0000F576 894D18              <1> 	mov	[ebp+24], ecx ; return to user with ecx value 
  7942                              <1> sysalloc_wrong:
  7943                              <1> 	; eax = 0FFFFFFFFh
  7944 0000F579 A3[64030300]        <1> 	mov	[u.r0], eax
  7945 0000F57E E9F7D9FFFF          <1> 	jmp	error
  7946                              <1> sysalloc_4:
  7947 0000F583 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; ebp points to user's registers
  7948 0000F589 894518              <1> 	mov	[ebp+24], eax ; return to user with ecx value 
  7949 0000F58C 895D10              <1> 	mov	[ebp+16], ebx ; new value of ebx (rounded up)
  7950 0000F58F 89C1                <1> 	mov	ecx, eax ; byte count (from 'deallocate_user_pages')
  7951 0000F591 5A                  <1> 	pop	edx ; ** ; discard (another) byte count
  7952 0000F592 58                  <1> 	pop	eax ; *
  7953 0000F593 A3[64030300]        <1> 	mov	[u.r0], eax ; physical address
  7954                              <1> 	
  7955 0000F598 51                  <1> 	push	ecx ; 20/08/2017
  7956                              <1> 	;
  7957                              <1> 	; Write newly allocated contiguous (physical) pages
  7958                              <1> 	; on page dir and page tables of current user/process	
  7959                              <1> 	; as PRESENT, USER, WRITABLE
  7960                              <1> 	; (then clear allocated pages)
  7961 0000F599 E8416AFFFF          <1> 	call	allocate_user_pages
  7962                              <1> 	;jnc	sysret ; OK! return to process with success...
  7963                              <1> 
  7964                              <1> 	; 20/08/2017 ('sysdma' modification)
  7965 0000F59E 59                  <1> 	pop	ecx
  7966 0000F59F A1[64030300]        <1> 	mov	eax, [u.r0]   ; physical address (of the block)
  7967                              <1> 
  7968 0000F5A4 721D                <1> 	jc	short sysalloc_6
  7969                              <1> 
  7970 0000F5A6 833D[44750100]FF    <1> 	cmp	dword [dma_addr], 0FFFFFFFFh ; -1	
  7971 0000F5AD 0F82E7D9FFFF        <1> 	jb	sysret
  7972                              <1> 
  7973 0000F5B3 A3[44750100]        <1> 	mov	[dma_addr], eax ; save dma address for sysdma
  7974 0000F5B8 890D[48750100]      <1> 	mov	[dma_size], ecx ; save dma buff size for sysdma
  7975                              <1> 
  7976 0000F5BE E9D7D9FFFF          <1> 	jmp	sysret
  7977                              <1> 		
  7978                              <1> sysalloc_6:
  7979                              <1> 	;
  7980                              <1> 	; unexpected error ! insufficient memory !? conflict !?
  7981                              <1> 	; (!!?there is not a free page for a new page table?!!)
  7982                              <1> 	; We need to terminate process with error message !!!  
  7983                              <1> 	;
  7984 0000F5C3 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; ebp points to user's registers
  7985 0000F5C9 8B4D18              <1> 	mov	ecx, [ebp+24] ; byte count
  7986                              <1> 	
  7987                              <1> 	; 20/08/2017
  7988                              <1> 	;mov	eax, [u.r0]   ; physical address (of the block)
  7989                              <1> 	
  7990                              <1> 	;
  7991                              <1> 	; restore Memory Allocation Table Content
  7992 0000F5CC E8CB67FFFF          <1> 	call	deallocate_memory_block
  7993                              <1> 	;
  7994 0000F5D1 803D[7A660000]03    <1> 	cmp	byte [CRT_MODE], 3 ; 80x25 text mode?
  7995 0000F5D8 7407                <1> 	je	short sysalloc_7 ; yes
  7996                              <1> 	; Current mode is VGA (or CGA graphics) mode,
  7997                              <1> 	; We need to return to text mode for displaying
  7998                              <1> 	; error message just before 'sysexit'.  
  7999 0000F5DA B003                <1> 	mov	al, 3
  8000 0000F5DC E88623FFFF          <1> 	call	_set_mode
  8001                              <1> sysalloc_7:
  8002 0000F5E1 BE[28160100]        <1> 	mov	esi, beep_Insufficient_Memory ; error message
  8003 0000F5E6 E81A76FFFF          <1> 	call	print_msg ; print/display the message
  8004 0000F5EB B801000000          <1> 	mov	eax, 1 ; ax=1 is needed for 'sysexit' procedure
  8005 0000F5F0 E92CDBFFFF          <1> 	jmp	sysexit ; and terminate the process !
  8006                              <1> 
  8007                              <1> sysdalloc:
  8008                              <1> 	; 19/02/2017 - TRDOS 386 (TRDOS v2.0)
  8009                              <1> 	; (TRDOS 386 feature only!)
  8010                              <1> 	;
  8011                              <1> 	; Deallocate Memory Block/Pages (for user)
  8012                              <1> 	; (Complementary call for sysalloc.)	
  8013                              <1> 	;
  8014                              <1> 	; INPUT ->
  8015                              <1> 	;	EBX = Virtual address (for user)
  8016                              <1> 	;	      (will be rounded up to page border)
  8017                              <1> 	;	ECX = Byte Count
  8018                              <1> 	;	     (will be adjusted to page borders)
  8019                              <1> 	;	If ICX = 0
  8020                              <1> 	;	   nothing to do
  8021                              <1> 	;	If EBX + ECX > User's ESP
  8022                              <1> 	;	   nothing to do		
  8023                              <1> 	; 
  8024                              <1> 	; Note: u.break control may be included in future versions	
  8025                              <1> 	;
  8026                              <1> 	; OUTPUT ->
  8027                              <1> 	;	If CF = 0
  8028                              <1> 	;	   EAX = Deallocated memory bytes
  8029                              <1> 	;	   EBX = Virtual address (as rounded up)	
  8030                              <1> 	;	IF CF = 1
  8031                              <1> 	;	   EAX = 0
  8032                              <1> 	;
  8033                              <1> 	; Note:	Main purpose of this call is to deallocate/release
  8034                              <1> 	;	previously allocated (physically) contiguous memory
  8035                              <1> 	;	pages but beginning (virtual) address may not be
  8036                              <1> 	;	followed by physically contiguous pages. So, this
  8037                              <1> 	;	system call will deallocate user's virtually
  8038                              <1> 	;	contiguous memory pages. Also, there is not any
  8039                              <1> 	;	objections to use this system call without sysalloc
  8040                              <1> 	;	system call; only possible objection is to lost data
  8041                              <1> 	;	within user's memory space, if the beginning address
  8042                              <1> 	;	and size is not proper.
  8043                              <1> 	;
  8044                              <1> 	; Note: Empty page tables will not be deallocated!!!
  8045                              <1> 	;       (they will be deallocated at process termination)
  8046                              <1> 	;
  8047                              <1> 	; Note: When the program terminates itself or when it is 
  8048                              <1> 	;	terminated by operating system kernel, all allocated
  8049                              <1> 	;	memory pages will be deallocated during termination
  8050                              <1> 	;	stage. So, 'sysdalloc' is not necessary except 
  8051                              <1> 	;	forgiving memory block to other programs/processes.
  8052                              <1> 	;	
  8053 0000F5F5 8B15[5C030300]      <1> 	mov	edx, [u.sp]
  8054 0000F5FB 8B420C              <1> 	mov	eax, [edx+12] ; user's stack pointer
  8055 0000F5FE 29C8                <1> 	sub	eax, ecx ; esp - byte count
  8056 0000F600 24FC                <1> 	and	al, 0FCh ; dword alignment
  8057 0000F602 39D8                <1> 	cmp	eax, ebx
  8058 0000F604 7220                <1> 	jb	short sysdalloc_err ; deallocation overlaps with stack 	
  8059                              <1> 
  8060 0000F606 31C0                <1> 	xor	eax, eax
  8061 0000F608 21C9                <1> 	and	ecx, ecx
  8062 0000F60A 7407                <1> 	jz	short sysdalloc_2
  8063                              <1> 	
  8064 0000F60C E8D968FFFF          <1> 	call	deallocate_user_pages
  8065 0000F611 7213                <1> 	jc	short sysdalloc_err
  8066                              <1> 
  8067                              <1> sysdalloc_2:
  8068 0000F613 A3[64030300]        <1> 	mov	[u.r0], eax
  8069 0000F618 8B2D[60030300]      <1> 	mov	ebp, [u.usp]
  8070 0000F61E 895D10              <1> 	mov	[ebp+16], ebx ; new value of ebx
  8071 0000F621 E974D9FFFF          <1> 	jmp	sysret
  8072                              <1> 
  8073                              <1> sysdalloc_err:
  8074 0000F626 A3[64030300]        <1> 	mov	[u.r0], eax ; 0
  8075 0000F62B E94AD9FFFF          <1> 	jmp	error
  8076                              <1> 
  8077                              <1> syscalbac:
  8078                              <1> 	; SYS CALLBACK
  8079                              <1> 	; 03/08/2020
  8080                              <1> 	; 16/04/2017
  8081                              <1> 	; 14/04/2017
  8082                              <1> 	; 13/04/2017
  8083                              <1> 	; 28/02/2017
  8084                              <1> 	; 26/02/2017
  8085                              <1> 	; 24/02/2017
  8086                              <1> 	; 21/02/2017 - TRDOS 386 (TRDOS v2.0)
  8087                              <1> 	; (TRDOS 386 feature only!)
  8088                              <1> 	;
  8089                              <1> 	; Link or unlink IRQ callback service to/from user (ring 3)	
  8090                              <1> 	;
  8091                              <1> 	; INPUT ->
  8092                              <1> 	;	BL = IRQ number (Hardware interrupt request number)
  8093                              <1> 	;	     (0 t0 15 but IRQ 0,1,2,6,8,14,15 are prohibited)
  8094                              <1> 	;	     IRQ numbers 3,4,5,7,9,10,11,12,13 are valid
  8095                              <1> 	;	     (numbers >15 are invalid)
  8096                              <1> 	;
  8097                              <1> 	;	BH = 0 = Unlink IRQ (in BL) from user (ring 3) service
  8098                              <1> 	;	     1 = Link IRQ by using Signal Response Byte method
  8099                              <1> 	;	     2 = Link IRQ by using Callback service method 		
  8100                              <1> 	;	     3 = Link IRQ by using Auto Increment S.R.B. method 	
  8101                              <1> 	;	    >3 = invalid 
  8102                              <1> 	;	
  8103                              <1> 	;	CL = Signal Return/Response Byte value 
  8104                              <1> 	;
  8105                              <1> 	;	If BH = 3, kernel will put a counter value  ; 03/08/2020
  8106                              <1> 	;	          (into the S.R.B. addr)
  8107                              <1> 	;		  between 0 to 255. (start value = CL+1)
  8108                              <1> 	;	
  8109                              <1> 	;	NOTE: counter value, for example: even and odd numbers
  8110                              <1> 	;	      may be used for -audio- DMA buffer switch 
  8111                              <1> 	;	      within double buffer method, etc. 		
  8112                              <1> 	;
  8113                              <1> 	;	EDX = Signal return (Response) byte address
  8114                              <1> 	;	       		  - or -
  8115                              <1> 	;	      Interrupt/Callback service/routine address
  8116                              <1> 	; 	
  8117                              <1> 	;	      (virtual address in user's memory space)
  8118                              <1> 	;
  8119                              <1> 	; OUTPUT ->
  8120                              <1> 	;	CF = 0 & EAX = 0 -> Successful setting
  8121                              <1> 	;	CF = 1 & EAX > 0 -> IRQ is prohibited or locked 
  8122                              <1> 	;			by another process
  8123                              <1> 	;		 eax = ERR_PERM_DENIED -> prohibited or locked
  8124                              <1> 	;		 eax = ERR_INV_PARAMETER -> 
  8125                              <1> 	;		       invalid parameter/option or bad address
  8126                              <1> 	;
  8127                              <1> 	;	NOTE: Timer callbacks are set by using 'systimer'
  8128                              <1> 	;	      system call (IRQ 0, PIT and IRQ 8, RTC)
  8129                              <1> 	;
  8130                              <1> 	;	      Direct keyboard access is performed by using
  8131                              <1> 	;	      Keyboard Interrupt (INT 32h)	 	
  8132                              <1> 	;	
  8133                              <1> 	;	      It is prohibited here because:
  8134                              <1> 	;		1) Signal Response Byte method has not advantage
  8135                              <1> 	;		   against INT 32h, function AH = 1. Also,
  8136                              <1> 	;		   keyboard service interrupt will return with
  8137                              <1> 	;		   ascii and scan codes (AL, AH) while
  8138                              <1> 	;		   SRB method has only 1 byte space for ascii code
  8139                              <1> 	;		   or scan code. One byte signal response is used 
  8140                              <1> 	;		   for ensuring very simple and very fast
  8141                              <1> 	;		   virtual to physical memory address conversion
  8142                              <1> 	;		   without any memory page crossover risk. 
  8143                              <1> 	;		   (Otherwise double page conversion or word 
  8144                              <1> 	;		   alignment would be needed.)
  8145                              <1> 	;		2) Badly written user code (callback code)
  8146                              <1> 	;		   can prevent keyboard and timesharing functions
  8147                              <1> 	;		   of the operating system via continuous and long
  8148                              <1> 	;		   keyboard event handling by callback service.
  8149                              <1> 	;		   (It can cause to lose immediate keystroke 
  8150                              <1> 	;		   response from hardware to user.)
  8151                              <1> 	;		3) If user will check any keyboard events, 'getkey'
  8152                              <1> 	;		   (or 'getchar') must have more priority than other
  8153                              <1> 	;		   (video etc.) events because only control ability
  8154                              <1> 	;		   on a procedural infinite loop is a keyboard or
  8155                              <1> 	;		   mouse event. So user can use keyboard function
  8156                              <1> 	;		   at the end or at the beginning of a loop.
  8157                              <1> 	;		   In this case, INT 32h is used for that purpose
  8158                              <1> 	;		   and timer interrupt etc. callbacks can be used
  8159                              <1> 	;		   for dynamic and synchronized data refresh/transfer
  8160                              <1> 	;		   while cpu is in a static loop (without polling).
  8161                              <1> 	;		   Keyboard Int callback is not more useful because 
  8162                              <1> 	;		   already a manual check (a key is pressed or not)
  8163                              <1> 	;		   can be performed (via INT 32h, AH = 1) efficiently
  8164                              <1> 	;		   in a loop to prevent a locked infinitive loop.
  8165                              <1> 	;
  8166                              <1> 	;	    Disk IRQs (6,14,15) have been phohibited from ring 3 
  8167                              <1> 	;	    callback because, disk operations (file system services
  8168                              <1> 	;	    etc.) are independent from user program, for fast disk r/w.
  8169                              <1> 	;	    They are not more useful at ring 3 while they are in use
  8170                              <1> 	;	    by standard diskio functions which are mandatory part of 
  8171                              <1> 	;	    (monolithic) OS kernel and mainprog command interpreter.
  8172                              <1> 	;	    INT 33h diskio functions are enough for user level disk
  8173                              <1> 	;	    r/w.				
  8174                              <1> 	;
  8175                              <1> 	; TRDOS 386 - IRQ CALLBACK structures (parameters):
  8176                              <1> 	;	
  8177                              <1> 	;	   [u.irqlock] = 1 word, IRQ flags (0-15) that indicates
  8178                              <1> 	;			which IRQs are locked by (that) user.
  8179                              <1> 	;		        Lock and unlock (by user) will change
  8180                              <1> 	;			these flags or 'terminate process' (sysexit)
  8181                              <1> 	;			will clear these flags and unlock those IRQs.
  8182                              <1> 	;			               
  8183                              <1> 	;		   	Bit 0 is for IRQ 0 and Bit 15 is for IRQ 15
  8184                              <1> 	;
  8185                              <1> 	;	   IRQ(x).owner	 : 1 byte, user, [u.uno], 0 = free (unlocked)	
  8186                              <1> 	;
  8187                              <1> 	;	   IRQ(x).method : 1 byte for callback method & status
  8188                              <1> 	;			   0 = Signal Response Byte method
  8189                              <1> 	;			   1 = Callback service method
  8190                              <1> 	;			   >1 = invalid for current 'syscalback'.
  8191                              <1> 	;			or(+) 80h = IRQ is in use by system (ring 0)
  8192                              <1> 	;			            function (audio etc.) or
  8193                              <1> 	;			   	    a device driver.	   	
  8194                              <1> 	;			(system function will ignore the lock/owner)
  8195                              <1> 	;
  8196                              <1> 	;	   IRQ(x).srb	: 1 byte, Signal Return/Response byte value
  8197                              <1> 	;			  (a fixed value by user or a counter value
  8198                              <1> 	;			 from 0 to 255, which is increased by every
  8199                              <1> 	;			 interrupt just before putting it into 
  8200                              <1> 	;			 the Signal Response byte address
  8201                              <1> 	;			 (This is not used in callback serv method)
  8202                              <1> 	;	    	  
  8203                              <1> 	;	   IRQ(x).addr	: 1 dword
  8204                              <1> 	;			  Signal Response Byte address (physical)
  8205                              <1> 	;			  		-or-
  8206                              <1> 	;			  Callback service address (virtual)
  8207                              <1> 	;
  8208                              <1> 	;	   IRQ(x).dev	: 1 byte
  8209                              <1> 	;			  0 = Default device or kernel function
  8210                              <1> 	;			  		-or-
  8211                              <1> 	;			  1-255 = Assigned device driver number
  8212                              <1> 	;
  8213                              <1> 	;	   (x) = 3,4,5,7,9,10,11,12,13
  8214                              <1> 	;
  8215                              <1> 	;	
  8216                              <1> 	;	NOTE: If user's process/program calls the kernel (INT 40h)
  8217                              <1> 	;	      while it is already running in a (ring 3) callback
  8218                              <1> 	;	      service, kernel will force (convert) system call to
  8219                              <1> 	;	      'sysrele' (sys release). So, this feature provides
  8220                              <1> 	;	      easy and simple usage of callback services without
  8221                              <1> 	;	      falling into deepless <please 'callback me' then 
  8222                              <1> 	;	      let me 'callback you'> cycles! (User must return
  8223                              <1> 	;	      from callback service by using 'sysrele' system
  8224                              <1> 	;	      call, without a significant delay. Otherwise user
  8225                              <1> 	;	      process/program may be late to catch the next event
  8226                              <1> 	;	      within same callback purpose.	    		 	
  8227                              <1> 	;
  8228                              <1> 
  8229 0000F630 30C0                <1> 	xor	al, al ; the caller is 'syscalbac' sign/flag
  8230 0000F632 E865180000          <1>  	call	set_irq_callback_service
  8231                              <1> 	; 16/04/2017
  8232 0000F637 A3[64030300]        <1> 	mov	[u.r0], eax
  8233 0000F63C 0F8358D9FFFF        <1> 	jnc	sysret
  8234 0000F642 A3[C8030300]        <1> 	mov	dword [u.error], eax
  8235 0000F647 E92ED9FFFF          <1> 	jmp	error
  8236                              <1> 
  8237                              <1> sysfpstat:
  8238                              <1> 	; 28/02/2017 - TRDOS 386 (TRDOS v2.0)
  8239                              <1> 	; (TRDOS 386 feature only!)
  8240                              <1> 	;
  8241                              <1> 	; Set or reset FPU registers save/restore option (for user)
  8242                              <1> 	;	       (during software task switching, wswap-rswap)
  8243                              <1> 	;
  8244                              <1> 	; INPUT ->
  8245                              <1> 	;	BL = 0 -> reset
  8246                              <1> 	;	BL = 1 -> set (FPU register will be saved and restored)
  8247                              <1> 	;	
  8248                              <1> 	; OUTPUT ->
  8249                              <1> 	;	cf = 0 -> no error, FPU is ready... 
  8250                              <1> 	;		  (EAX = 0)
  8251                              <1> 	;	Cf = 1 -> error, 80387 FPU is not ready !
  8252                              <1> 	;		  (EAX = 0FFFFFFFFh)
  8253                              <1> 
  8254 0000F64C 31C0                <1> 	xor	eax, eax
  8255 0000F64E 803D[3C6B0100]00    <1> 	cmp	byte [fpready], 0
  8256 0000F655 7613                <1> 	jna	short sysfpstat_err	
  8257                              <1> 
  8258 0000F657 80E301              <1> 	and	bl, 1 ; use BIT 0 only !
  8259 0000F65A 881D[DA030300]      <1> 	mov	[u.fpsave], bl
  8260 0000F660 A3[64030300]        <1> 	mov	[u.r0], eax ; 0
  8261 0000F665 E930D9FFFF          <1> 	jmp	sysret	 	
  8262                              <1> 
  8263                              <1> sysfpstat_err:
  8264 0000F66A 48                  <1> 	dec 	eax ; 0FFFFFFFFh
  8265 0000F66B A3[64030300]        <1> 	mov 	[u.r0], eax ; -1
  8266 0000F670 E905D9FFFF          <1> 	jmp 	error
  8267                              <1> 
  8268                              <1> sysdelete: ; Delete (Remove, Unlink) File
  8269                              <1> 	; 29/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8270                              <1> 	;	
  8271                              <1>         ; INPUT ->
  8272                              <1>         ;          EBX = File name (ASCIIZ string) address
  8273                              <1> 	; OUTPUT ->
  8274                              <1> 	;          cf = 0 -> eax = 0
  8275                              <1> 	;          cf = 1 -> Error code in AL
  8276                              <1> 	;
  8277                              <1> 	; Modified Registers: EAX (at the return of system call)
  8278                              <1> 	;   
  8279                              <1> 
  8280 0000F675 89DE                <1> 	mov	esi, ebx
  8281                              <1> 	; file name is forced, change directory as temporary
  8282                              <1> 	;mov	ax, 1
  8283                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset
  8284                              <1> 	;call	set_working_path 
  8285 0000F677 E8680B0000          <1> 	call	set_working_path_x
  8286 0000F67C 731D                <1> 	jnc	short sysdelete_1
  8287                              <1> 
  8288 0000F67E 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  8289 0000F680 7505                <1> 	jnz	short sysdelete_err
  8290                              <1> 	; eax = 0
  8291                              <1> sysdelete_path_err:
  8292 0000F682 B813000000          <1> 	mov	eax, ERR_INV_PATH_NAME ; 'bad path name !'
  8293                              <1> sysdelete_err:
  8294 0000F687 A3[64030300]        <1> 	mov	[u.r0], eax
  8295 0000F68C A3[C8030300]        <1> 	mov	[u.error], eax
  8296 0000F691 E8230C0000          <1> 	call 	reset_working_path
  8297 0000F696 E9DFD8FFFF          <1> 	jmp	error
  8298                              <1> sysdelete_1:
  8299                              <1> 	;mov	esi, FindFile_Name
  8300 0000F69B 66B80018            <1> 	mov	ax, 1800h ; Only files
  8301 0000F69F E87B94FFFF          <1> 	call	find_first_file
  8302 0000F6A4 72E1                <1> 	jc	short sysdelete_err
  8303                              <1> sysdelete_2:
  8304                              <1> 	; check file attributes
  8305                              <1> 
  8306                              <1> 	;test	bl, 17 ; system, hidden, readonly, directory
  8307 0000F6A6 F6C307              <1>         test	bl, 7 ; system, hidden, readonly 
  8308 0000F6A9 7407                <1>         jz	short sysdelete_3
  8309                              <1> 
  8310 0000F6AB B80B000000          <1>         mov	eax, ERR_FILE_ACCESS ; 11 = 'permission denied !'
  8311 0000F6B0 EBD5                <1>         jmp	short sysdelete_err
  8312                              <1> sysdelete_3:
  8313 0000F6B2 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  8314 0000F6B5 7407                <1> 	jz	short sysdelete_4
  8315 0000F6B7 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME ; 26 = 'invalid file name !'
  8316 0000F6BC EBC9                <1>         jmp	short sysdelete_err
  8317                              <1> sysdelete_4:
  8318                              <1> 	;mov	bh, [LongName_EntryLength]
  8319 0000F6BE 883D[AE680100]      <1> 	mov	[DelFile_LNEL], bh ; Long name entry length (if > 0)
  8320                              <1> 	; edi = Directory Entry Offset (DirBuff)
  8321                              <1> 	; esi = Directory Entry (FFF Structure)
  8322 0000F6C4 E8D3BDFFFF          <1> 	call	remove_file
  8323 0000F6C9 72BC                <1> 	jc	short sysdelete_err
  8324                              <1> sysrmdir_5:
  8325 0000F6CB 31C0                <1> 	xor	eax, eax ; 0
  8326 0000F6CD A3[64030300]        <1> 	mov	[u.r0], eax
  8327                              <1> 	;mov	[u.error], eax
  8328 0000F6D2 E8E20B0000          <1> 	call 	reset_working_path
  8329 0000F6D7 E9BED8FFFF          <1> 	jmp	sysret
  8330                              <1> 
  8331                              <1> 
  8332                              <1> sysrmdir: ; Remove (Unlink) Directory
  8333                              <1> 	; 29/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8334                              <1> 	;	
  8335                              <1>         ; INPUT ->
  8336                              <1>         ;          EBX = Pointer to directory name
  8337                              <1> 	; OUTPUT ->
  8338                              <1> 	;          cf = 0 -> eax = 0
  8339                              <1> 	;          cf = 1 -> Error code in AL
  8340                              <1> 	;
  8341                              <1> 	; Modified Registers: EAX (at the return of system call)
  8342                              <1> 	;  
  8343                              <1> 
  8344 0000F6DC 803D[B3030300]00    <1> 	cmp	byte [u.uno], 0  ; root (super user) ?
  8345 0000F6E3 7614                <1> 	jna	short sysrmdir_0
  8346                              <1> 
  8347                              <1> 	;mov	dword [u.r0], ERR_PERM_DENIED
  8348 0000F6E5 B80B000000          <1> 	mov	eax, ERR_PERM_DENIED ; ERR_NOT_SUPERUSER
  8349 0000F6EA A3[64030300]        <1> 	mov	[u.r0], eax
  8350 0000F6EF A3[C8030300]        <1> 	mov	[u.error], eax
  8351 0000F6F4 E981D8FFFF          <1> 	jmp	error
  8352                              <1> 
  8353                              <1> sysrmdir_0:
  8354 0000F6F9 89DE                <1> 	mov	esi, ebx
  8355                              <1> 	; file name is forced, change directory as temporary
  8356                              <1> 	;mov	ax, 1
  8357                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset
  8358                              <1> 	;call	set_working_path 
  8359 0000F6FB E8E40A0000          <1> 	call	set_working_path_x
  8360 0000F700 731D                <1> 	jnc	short sysrmdir_1
  8361                              <1> 
  8362 0000F702 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  8363 0000F704 7505                <1> 	jnz	short sysrmdir_err
  8364                              <1> 	; eax = 0
  8365                              <1> sysrmdir_not_found:
  8366 0000F706 B80C000000          <1> 	mov	eax, ERR_DIR_NOT_FOUND ; Directory not found !
  8367                              <1> sysrmdir_err:
  8368 0000F70B A3[64030300]        <1> 	mov	[u.r0], eax
  8369 0000F710 A3[C8030300]        <1> 	mov	[u.error], eax
  8370 0000F715 E89F0B0000          <1> 	call 	reset_working_path
  8371 0000F71A E95BD8FFFF          <1> 	jmp	error
  8372                              <1> sysrmdir_1:
  8373                              <1> 	;mov	esi, FindFile_Name
  8374 0000F71F 66B81008            <1> 	mov	ax, 0810h ; Only directories
  8375 0000F723 E8F793FFFF          <1> 	call	find_first_file
  8376 0000F728 7306                <1> 	jnc	short sysrmdir_2
  8377                              <1> 
  8378                              <1> 	; eax = 2 (File not found !)
  8379 0000F72A 3C02                <1> 	cmp	al, 2 ; ERR_NOT_FOUND
  8380 0000F72C 74D8                <1> 	je	short sysrmdir_not_found
  8381 0000F72E EBDB                <1> 	jmp	short sysrmdir_err
  8382                              <1> sysrmdir_2:
  8383                              <1> 	; check directory attributes
  8384                              <1> 
  8385 0000F730 F6C307              <1>         test	bl, 7 ; system, hidden, readonly 
  8386 0000F733 7407                <1>         jz	short sysrmdir_3
  8387                              <1> 
  8388 0000F735 B80B000000          <1>         mov	eax, ERR_DIR_ACCESS ; 11 = 'permission denied !'
  8389 0000F73A EBCF                <1>         jmp	short sysrmdir_err
  8390                              <1> sysrmdir_3:
  8391 0000F73C 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  8392 0000F73F 7407                <1> 	jz	short sysrmdir_4
  8393                              <1> 	;mov	eax, ERR_NOT_DIR ; 'not a valid directory !'
  8394 0000F741 B813000000          <1> 	mov	eax, ERR_INV_PATH_NAME ; 'bad path name !'
  8395 0000F746 EBC3                <1>         jmp	short sysrmdir_err
  8396                              <1> sysrmdir_4:
  8397                              <1> 	;mov	bh, [LongName_EntryLength]
  8398 0000F748 883D[AE680100]      <1> 	mov	[DelFile_LNEL], bh ; Long name entry length (if > 0)
  8399                              <1> 	; edi = Directory Entry Offset (DirBuff)
  8400                              <1> 	; esi = Directory Entry (FFF Structure)
  8401 0000F74E E8A19AFFFF          <1> 	call	delete_sub_directory
  8402 0000F753 0F8372FFFFFF        <1> 	jnc	sysrmdir_5
  8403                              <1> ;	jc	short sysrmdir_6
  8404                              <1> ;
  8405                              <1> ;	xor	eax, eax ; 0
  8406                              <1> ;sysrmdir_5:
  8407                              <1> ;	mov	[u.r0], eax
  8408                              <1> ;	;mov	[u.error], eax
  8409                              <1> ;	call 	reset_working_path
  8410                              <1> ;	jmp	sysret
  8411                              <1> sysrmdir_6:
  8412 0000F759 A3[64030300]        <1> 	mov	[u.r0], eax
  8413 0000F75E A3[C8030300]        <1> 	mov	[u.error], eax
  8414                              <1> 
  8415 0000F763 09C0                <1> 	or	eax, eax ; EAX = 0 -> Directory not empty!
  8416 0000F765 741C                <1> 	jz	short sysrmdir_9
  8417                              <1> 
  8418                              <1> 	; EAX > 0 -> Error code in AL (or AX or EAX)
  8419                              <1> 
  8420 0000F767 833D[62660100]01    <1> 	cmp	dword [FAT_ClusterCounter], 1
  8421 0000F76E 7209                <1> 	jb	short sysrmdir_8
  8422                              <1> sysrmdir_7:
  8423                              <1> 	; ESI = Logical DOS Drive Description Table address	
  8424 0000F770 66BB00FF            <1> 	mov	bx, 0FF00h ; BH = FFh -> use ESI for Drive parameters
  8425                              <1> 	           ; BL = 0 -> Recalculate free cluster count
  8426 0000F774 E807D3FFFF          <1> 	call	calculate_fat_freespace	
  8427                              <1> sysrmdir_8:
  8428 0000F779 E83B0B0000          <1> 	call 	reset_working_path
  8429 0000F77E E9F7D7FFFF          <1> 	jmp	error
  8430                              <1> 
  8431                              <1> sysrmdir_9:
  8432 0000F783 A1[62660100]        <1> 	mov	eax, [FAT_ClusterCounter]
  8433 0000F788 09C0                <1> 	or	eax, eax ; 0 ?
  8434 0000F78A 0F847BFFFFFF        <1> 	jz	sysrmdir_err
  8435                              <1> 	; ESI = Logical DOS Drive Description Table address	
  8436 0000F790 66BB01FF            <1> 	mov	bx, 0FF01h ; BH = FFh -> use ESI for Drive parameters
  8437                              <1> 	           ; BL = 1 -> add free clusters
  8438 0000F794 E8E7D2FFFF          <1> 	call	calculate_fat_freespace
  8439 0000F799 09C9                <1> 	or	ecx, ecx
  8440 0000F79B 74DC                <1>         jz	short sysrmdir_8 ; ecx = 0 -> OK
  8441                              <1> 	; ecx > 0 -> Error (Recalculation is needed)
  8442 0000F79D EBD1                <1> 	jmp	short sysrmdir_7
  8443                              <1> 
  8444                              <1> 
  8445                              <1> syschdir: ; Change Current (Working) Drive & Directory (for user)
  8446                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8447                              <1> 	;	
  8448                              <1>         ; INPUT ->
  8449                              <1>         ;          EBX = Directory name (ASCIIZ string) address
  8450                              <1> 	; OUTPUT ->
  8451                              <1> 	;          cf = 0 -> eax = 0
  8452                              <1> 	;          cf = 1 -> Error code in AL
  8453                              <1> 	;
  8454                              <1> 	; Modified Registers: EAX (at the return of system call)
  8455                              <1> 	;
  8456                              <1> 	; NOTE: If drive name is not included, only the working
  8457                              <1> 	; directory (for user, not for drive/OS) will be chanded.
  8458                              <1> 	; If there is a drive name (as A:, B:, C:, D: etc.)
  8459                              <1> 	; at the beginning of the ASCIIZ (directory) string,
  8460                              <1> 	; working drive and working directory (for user) 
  8461                              <1> 	; will be changed together.
  8462                              <1> 	; (When the program is terminated, MainProg -internal 
  8463                              <1> 	; shell- will reset working directory to the previous
  8464                              <1> 	; -current- logical drive's current directory again.) 	
  8465                              <1>   
  8466 0000F79F 89DE                <1> 	mov	esi, ebx
  8467                              <1> 	; file name is not forced, change directory as temporary
  8468 0000F7A1 31C0                <1> 	xor	eax, eax
  8469                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset
  8470                              <1> 	;call	set_working_path 
  8471 0000F7A3 E8400A0000          <1> 	call	set_working_path_xx
  8472 0000F7A8 731D                <1> 	jnc	short syschdir_ok
  8473 0000F7AA 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  8474 0000F7AC 7505                <1> 	jnz	short syschdir_err
  8475                              <1> 	; eax = 0
  8476                              <1> syschdir_not_found:
  8477 0000F7AE B80C000000          <1> 	mov	eax, ERR_DIR_NOT_FOUND ; Directory not found !
  8478                              <1> syschdir_err:
  8479 0000F7B3 A3[64030300]        <1> 	mov	[u.r0], eax
  8480 0000F7B8 A3[C8030300]        <1> 	mov	[u.error], eax
  8481 0000F7BD E8F70A0000          <1> 	call 	reset_working_path
  8482 0000F7C2 E9B3D7FFFF          <1> 	jmp	error
  8483                              <1> syschdir_ok:
  8484 0000F7C7 31C0                <1> 	xor	eax, eax ; 0
  8485 0000F7C9 A3[64030300]        <1> 	mov	[u.r0], eax
  8486                              <1> 	;mov	[u.error], eax
  8487 0000F7CE E9C7D7FFFF          <1> 	jmp	sysret
  8488                              <1> 
  8489                              <1> 
  8490                              <1> syschmod: ; Get & Change File (or Directory) Attributes
  8491                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8492                              <1> 	;	
  8493                              <1>         ; INPUT ->
  8494                              <1>         ;          EBX = File/Directory (ASCIIZ) name address
  8495                              <1> 	;	    CL = New attributes (if CL < 40h)
  8496                              <1> 	;	    CL >= 40h -> Get File Attributes		
  8497                              <1> 	; OUTPUT ->
  8498                              <1> 	;          cf = 0 -> EAX = File attributes (in AL)
  8499                              <1> 	;          cf = 1 -> Error code in AL
  8500                              <1> 	;
  8501                              <1> 	; Modified Registers: EAX (at the return of system call)
  8502                              <1> 	;  
  8503                              <1> 	; MSDOS File Attributes:    (bit value of attrib byte)
  8504                              <1> 	;	ATTR_READ_ONLY	=	01h  (bit 0, 'R')
  8505                              <1> 	;	ATTR_HIDDEN	=	02h  (bit 1, 'H')
  8506                              <1> 	;	ATTR_SYSTEM	=	04h  (bit 2, 'S')
  8507                              <1> 	;	ATTR_VOLUME_ID	=	08h  (bit 3)
  8508                              <1> 	;	ATTR_DIRECTORY	=	10h  (bit 4)
  8509                              <1> 	;	ATTR_ARCHIVE	=	20h  (bit 5, 'A')
  8510                              <1> 	;	ATTR_LONG_NAME	=	ATTR_READONLY |
  8511                              <1> 	;				ATTR_HIDDEN |
  8512                              <1> 	;				ATTR_SYSTEM |
  8513                              <1> 	;				ATTR_VOLUME_ID				
  8514                              <1> 	;	The upper two bits of attributes must be 0.
  8515                              <1> 
  8516                              <1> 	; Note:	* If ATTR_DIRECTORY is set, only directory names
  8517                              <1> 	;	  will be searched (and S,H,R,A attributeds of 
  8518                              <1> 	;	  the directory will be changed.)
  8519                              <1> 	;	* If ATTR_VOLUME_ID is set, 'syschmod' system call
  8520                              <1> 	;	  will return with 'permission denied' error.
  8521                              <1> 	;	* If ATTR_DIRECTORY is not set, only file names
  8522                              <1> 	;	  will be searched (and S,H,R,A attributes of the
  8523                              <1> 	;	  file will be changed.)
  8524                              <1> 	;
  8525                              <1> 	; (Ony Super User can change S,H,R attributes.) 
  8526                              <1> 
  8527 0000F7D3 80F940              <1> 	cmp	cl, 40h	
  8528 0000F7D6 7327                <1> 	jnb	short syschmod_0
  8529                              <1> 
  8530 0000F7D8 F6C108              <1> 	test	cl, 08h ; ATTR_VOLUME_ID
  8531 0000F7DB 750E                <1> 	jnz	short syschmod_perm_err
  8532                              <1> 
  8533 0000F7DD 803D[B3030300]00    <1> 	cmp	byte [u.uno], 0  ; root (super user) ?
  8534 0000F7E4 7619                <1> 	jna	short syschmod_0
  8535                              <1> 
  8536                              <1> 	; Not super user..
  8537 0000F7E6 F6C107              <1> 	test	cl, 07h	; S,H,R attributes
  8538 0000F7E9 7414                <1> 	jz	short syschmod_0
  8539                              <1> 
  8540                              <1> syschmod_perm_err:
  8541                              <1> 	;mov	dword [u.r0], ERR_PERM_DENIED
  8542 0000F7EB B80B000000          <1> 	mov	eax, ERR_PERM_DENIED ; 'permission denied !'
  8543 0000F7F0 A3[64030300]        <1> 	mov	[u.r0], eax
  8544 0000F7F5 A3[C8030300]        <1> 	mov	[u.error], eax
  8545 0000F7FA E97BD7FFFF          <1> 	jmp	error
  8546                              <1> 
  8547                              <1> syschmod_0:
  8548 0000F7FF 880D[FC680100]      <1> 	mov	[Attributes], cl
  8549 0000F805 89DE                <1> 	mov	esi, ebx
  8550                              <1> 	; file name is forced, change directory as temporary
  8551                              <1> 	;mov	ax, 1
  8552                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset
  8553                              <1> 	;call	set_working_path 
  8554 0000F807 E8D8090000          <1> 	call	set_working_path_x
  8555 0000F80C 731D                <1> 	jnc	short syschmod_1
  8556 0000F80E 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  8557 0000F810 7505                <1> 	jnz	short syschmod_err
  8558                              <1> 	; eax = 0
  8559                              <1> syschmod_path_not_found:
  8560 0000F812 B813000000          <1> 	mov	eax, ERR_INV_PATH_NAME ; 'Bad path name !'
  8561                              <1> syschmod_err:
  8562 0000F817 A3[64030300]        <1> 	mov	[u.r0], eax
  8563 0000F81C A3[C8030300]        <1> 	mov	[u.error], eax
  8564 0000F821 E8930A0000          <1> 	call 	reset_working_path
  8565 0000F826 E94FD7FFFF          <1> 	jmp	error
  8566                              <1> syschmod_1:
  8567 0000F82B B008                <1> 	mov	al, 08h ; Except volume labels (& long names)
  8568 0000F82D A0[FC680100]        <1> 	mov	al, [Attributes]
  8569 0000F832 2410                <1> 	and	al, 10h ;
  8570                              <1> 	;mov	esi, FindFile_Name
  8571                              <1> 	;mov	ax, 1800h ; Only files
  8572                              <1> 	;mov	ax, 0810h ; Only directories
  8573 0000F834 E8E692FFFF          <1> 	call	find_first_file
  8574                              <1> 	;jnc	short syschmod_2
  8575 0000F839 72DC                <1> 	jc	short syschmod_err
  8576                              <1> 
  8577                              <1> 	;; eax = 2 (File not found !)
  8578                              <1> 	;cmp	al, 2 ; ERR_NOT_FOUND
  8579                              <1> 	;jne	short syschmod_err
  8580                              <1> 
  8581                              <1> 	;and	byte [Attributes], 10h
  8582                              <1> 	;jz	short syschmod_err
  8583                              <1> 
  8584                              <1> 	;; Directory not found !
  8585                              <1> 	;mov	al, 3 ; ERR_PATH_NOT_FOUND
  8586                              <1> 	;jmp	short syschmod_err
  8587                              <1> 
  8588                              <1> syschmod_2:
  8589 0000F83B 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  8590 0000F83E 7407                <1> 	jz	short syschmod_3
  8591 0000F840 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME ; 'invalid file name !'
  8592 0000F845 EBD0                <1>         jmp	short syschmod_err
  8593                              <1> syschmod_3:
  8594                              <1> 	; EDI = Directory buffer entry offset/address
  8595                              <1> 	; BL = File (or Directory) Attributes 
  8596                              <1> 	; mov	bl, [EDI+0Bh]
  8597                              <1> 
  8598                              <1> 	; check directory attributes
  8599 0000F847 8A3D[FC680100]      <1> 	mov	bh, [Attributes] ; new attributes
  8600 0000F84D 80FF40              <1> 	cmp	bh, 40h  ;>=40 -> get file/directory attributes
  8601 0000F850 732D                <1> 	jnb	short syschmod_6
  8602                              <1> 
  8603                              <1> 	; set file/directory attributes
  8604 0000F852 F6C307              <1> 	test	bl, 7 ; system, hidden, readonly 
  8605 0000F855 7409                <1>         jz	short syschmod_4
  8606                              <1> 
  8607 0000F857 803D[B3030300]00    <1> 	cmp	byte [u.uno], 0  ; root (super user) ?
  8608 0000F85E 778B                <1> 	ja	short syschmod_perm_err
  8609                              <1> syschmod_4:
  8610 0000F860 66817F0CA101        <1> 	cmp	word [edi+DirEntry_NTRes], 01A1h ; Singlix FS
  8611 0000F866 7424                <1> 	je	short syschmod_7
  8612                              <1> 
  8613 0000F868 887F0B              <1> 	mov	[edi+0Bh], bh    ; Attributes (New!)
  8614                              <1> 
  8615 0000F86B C605[6C660100]02    <1> 	mov	byte [DirBuff_ValidData], 2 ; modified sign
  8616                              <1> 					    ; to force write	
  8617 0000F872 E8DDB8FFFF          <1> 	call 	save_directory_buffer
  8618 0000F877 729E                <1> 	jc	short syschmod_err
  8619                              <1> 
  8620                              <1> syschmod_5:
  8621 0000F879 8A1D[FC680100]      <1> 	mov	bl, [Attributes]
  8622                              <1> syschmod_6:
  8623 0000F87F 0FB6C3              <1> 	movzx	eax, bl
  8624 0000F882 A3[64030300]        <1> 	mov	[u.r0], eax
  8625                              <1> 	;mov	dword [u.error], 0
  8626 0000F887 E90ED7FFFF          <1> 	jmp	sysret
  8627                              <1> 
  8628                              <1> syschmod_7:
  8629 0000F88C 29C0                <1> 	sub	eax, eax
  8630 0000F88E 8A25[6A660100]      <1>         mov     ah, [DirBuff_DRV]
  8631 0000F894 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  8632 0000F899 01C6                <1>         add     esi, eax
  8633 0000F89B 807E04A1            <1>         cmp     byte [esi+LD_FSType], 0A1h
  8634 0000F89F 7307                <1> 	jnc	short syschmod_8
  8635 0000F8A1 B01D                <1> 	mov	al, ERR_INV_DATA ; 29 = Invalid Data
  8636 0000F8A3 E96FFFFFFF          <1> 	jmp	syschmod_err
  8637                              <1> 
  8638                              <1> syschmod_8:
  8639                              <1> 	; BH = New MS-DOS File Attributes
  8640 0000F8A8 88F8                <1> 	mov	al, bh ; File/Directory Attributes
  8641 0000F8AA 30E4                <1> 	xor	ah, ah ; Attributes in MS-DOS format sign	  
  8642 0000F8AC E8CCA3FFFF          <1> 	call	change_fs_file_attributes
  8643 0000F8B1 0F8260FFFFFF        <1> 	jc	syschmod_err
  8644 0000F8B7 EBC0                <1> 	jmp	short syschmod_5
  8645                              <1> 
  8646                              <1> 
  8647                              <1> sysdrive: ; Get/Set Current (Working) Drive (for user)
  8648                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8649                              <1> 	;	
  8650                              <1>         ; INPUT ->
  8651                              <1>         ;          BL = Logical DOS Drive number (0=A: ... 2=C:)
  8652                              <1> 	;	   If BL = 0FFh -> Get Current Drive 	
  8653                              <1> 	; OUTPUT ->
  8654                              <1> 	;          cf = 0 -> 
  8655                              <1> 	;		   AL = Current Drive number	
  8656                              <1> 	;		   AH = The Last Logical DOS Drive no.
  8657                              <1> 	;          cf = 1 -> Error code in AL
  8658                              <1> 	;
  8659                              <1> 	; Modified Registers: EAX (at the return of system call)
  8660                              <1> 	;
  8661                              <1> 	; NOTE: If the requested logical dos drive is ready, 
  8662                              <1> 	;	it's current current directory will be the user's
  8663                              <1> 	;	(program's) current directory.
  8664                              <1> 	;	(When the program is terminated, MainProg -internal 
  8665                              <1> 	;	shell- will reset the previous -current- logical drive
  8666                              <1> 	;       as current drive again).	
  8667                              <1>   
  8668 0000F8B9 80FBFF              <1> 	cmp	bl, 0FFh
  8669 0000F8BC 7435                <1> 	je	short sysdrive_ok
  8670 0000F8BE 3A1D[C6120100]      <1> 	cmp	bl, [Last_DOS_DiskNo]
  8671 0000F8C4 771E                <1> 	ja	short sysdrive_err	
  8672                              <1> 
  8673                              <1> 	; Save current drive and reset mode
  8674                              <1> 	; for 'reset_working_path' procedure (for MainProg)
  8675 0000F8C6 30C0                <1> 	xor	al, al
  8676 0000F8C8 66A3[386B0100]      <1> 	mov	[SWP_Mode], ax ; ah = 0
  8677 0000F8CE A0[465F0100]        <1> 	mov	al, [Current_Drv]
  8678 0000F8D3 FEC4                <1> 	inc	ah ; mov ah, 1
  8679 0000F8D5 66A3[3A6B0100]      <1> 	mov	[SWP_DRV], ax 
  8680                              <1> 
  8681 0000F8DB 88DA                <1> 	mov	dl, bl
  8682 0000F8DD E89A7EFFFF          <1> 	call	change_current_drive
  8683 0000F8E2 730F                <1> 	jnc	short sysdrive_ok
  8684                              <1> sysdrive_err:
  8685 0000F8E4 C705[64030300]0F00- <1> 	mov	dword [u.r0], ERR_DRV_NOT_RDY ; 'drive not ready !'
  8685 0000F8EC 0000                <1>
  8686 0000F8EE E987D6FFFF          <1> 	jmp	error
  8687                              <1> sysdrive_ok:
  8688 0000F8F3 A0[465F0100]        <1> 	mov	al, [Current_Drv]
  8689 0000F8F8 8A25[C6120100]      <1> 	mov	ah, [Last_DOS_DiskNo]
  8690 0000F8FE A3[64030300]        <1> 	mov	[u.r0], eax
  8691 0000F903 E992D6FFFF          <1> 	jmp	sysret
  8692                              <1> 
  8693                              <1> 
  8694                              <1> sysdir: ; Get Current (Working) Drive & Directory (for user)
  8695                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8696                              <1> 	;	
  8697                              <1>         ; INPUT ->
  8698                              <1>         ;          EBX = Current directory name buffer address
  8699                              <1> 	;		(Buffer length = 92 bytes)
  8700                              <1> 	; OUTPUT ->
  8701                              <1> 	;          AL = Current drive (0=A: .. 2=C:)
  8702                              <1> 	;	   If CF = 1 -> AL = error code
  8703                              <1> 	;
  8704                              <1> 	; Modified Registers: EAX (at the return of system call)
  8705                              <1> 	;
  8706                              <1> 	; Note: Required directory name buffer length may be 
  8707                              <1> 	;	<= 92 bytes for current TRDOS 386 version.
  8708                              <1> 	;	(7*12 name chars + 7 slash + 0)
  8709                              <1> 
  8710 0000F908 89E5                <1> 	mov	ebp, esp
  8711 0000F90A 83EC60              <1> 	sub	esp, 96
  8712 0000F90D 53                  <1> 	push	ebx ; User's buffer address
  8713 0000F90E 30D2                <1> 	xor	dl, dl ; 0 = current drive
  8714 0000F910 E863ADFFFF          <1>   	call	get_current_directory
  8715 0000F915 72CD                <1> 	jc	short sysdrive_err ; 'drive not ready !' error
  8716 0000F917 89E6                <1> 	mov	esi, esp ; System's buffer address
  8717 0000F919 5F                  <1> 	pop	edi  ; User's buffer address
  8718                              <1> 	; ecx = transfer (byte) count (<=92)
  8719 0000F91A E843F4FFFF          <1> 	call	transfer_to_user_buffer
  8720 0000F91F 89EC                <1> 	mov	esp, ebp
  8721 0000F921 730F                <1> 	jnc	short sysdir_ok
  8722                              <1> sysdir_err:
  8723 0000F923 C705[64030300]2E00- <1> 	mov	dword [u.r0], ERR_BUFFER  ; 'buffer error !'
  8723 0000F92B 0000                <1>
  8724 0000F92D E948D6FFFF          <1> 	jmp	error
  8725                              <1> sysdir_ok:	
  8726 0000F932 8A0D[465F0100]      <1> 	mov	cl, [Current_Drv]
  8727 0000F938 890D[64030300]      <1> 	mov	[u.r0], ecx
  8728 0000F93E E957D6FFFF          <1> 	jmp	sysret
  8729                              <1> 
  8730                              <1> 
  8731                              <1> sysldrvt: ; Get copy of Logical DOS Drive Description Table
  8732                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8733                              <1> 	;	
  8734                              <1>         ; INPUT ->
  8735                              <1> 	;	    BL = Logical DOS drive number (zero based)	
  8736                              <1>         ;          ECX = Logical DOS drv desc table buffer addr
  8737                              <1> 	;		(Buffer length = 256 bytes)
  8738                              <1> 	; OUTPUT ->
  8739                              <1> 	;          cf = 0 -> 
  8740                              <1> 	;		   AL = Current Drive number	
  8741                              <1> 	;		   AH = The Last Logical DOS Drive no.
  8742                              <1> 	;          cf = 1 -> Error code in AL
  8743                              <1> 	;		   AH = The Last Logical DOS Drive no.
  8744                              <1> 	;
  8745                              <1> 	; Modified Registers: EAX (at the return of system call)
  8746                              <1> 	;
  8747                              <1> 	; Note: Required description table buffer length is
  8748                              <1> 	;	256 bytes for current TRDOS 386 version.
  8749                              <1> 	
  8750 0000F943 89CF                <1> 	mov	edi, ecx ; Destination address (user space)
  8751 0000F945 88DC                <1> 	mov	ah, bl
  8752 0000F947 30C0                <1> 	xor	al, al
  8753 0000F949 BE00010900          <1> 	mov	esi, Logical_DOSDisks
  8754 0000F94E 01C6                <1> 	add	esi, eax ; Source address (system space)	 
  8755 0000F950 B900010000          <1> 	mov	ecx, 256 ; Byte count 
  8756                              <1> 			 ; Logical Dos Drv Desc Table size
  8757 0000F955 E808F4FFFF          <1> 	call	transfer_to_user_buffer
  8758 0000F95A 72C7                <1> 	jc	short sysdir_err
  8759 0000F95C 8A2D[C6120100]      <1> 	mov	ch, [Last_DOS_DiskNo]
  8760 0000F962 EBCE                <1> 	jmp	short sysdir_ok
  8761                              <1> 
  8762                              <1> 
  8763                              <1> systime: ; Get System Date&Time
  8764                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8765                              <1> 	;	
  8766                              <1>         ; INPUT -> BL =
  8767                              <1> 	;	    0 = Get Date&Time in Unix/Epoch format
  8768                              <1> 	;	    1 = Get Time in MSDOS format
  8769                              <1> 	;	    2 = Get Date in MSDOS format
  8770                              <1> 	;	    3 = Get Date&Time in MSDOS format
  8771                              <1> 	;	    4 & other values =
  8772                              <1> 	;		System timer ticks will be returned
  8773                              <1> 	;		in EAX and Carry Flag will be set.
  8774                              <1> 	;		(CF will not be set if BL = 4)	 	
  8775                              <1> 	; OUTPUT ->
  8776                              <1> 	;	For BL input = 3
  8777                              <1> 	;          EAX = Current Time (RTC)
  8778                              <1> 	;		AL = Second (DL in MSDOS)
  8779                              <1> 	;		AH = Minute (CL in MSDOS)
  8780                              <1> 	;	   	HW of EAX = Hour (CH in MSDOS)	
  8781                              <1> 	;	   EDX = Current System Date (RTC)
  8782                              <1> 	;		DL = Day (DL in MSDOS)
  8783                              <1> 	;		DH = Month (DH in MSDOS)
  8784                              <1> 	;		HW of EDX = Year (CX in MSDOS)	
  8785                              <1> 	;
  8786                              <1> 	;	For BL input = 2
  8787                              <1> 	;	   EAX = Current System Date (RTC)
  8788                              <1> 	;		DL = Day (DL in MSDOS)
  8789                              <1> 	;		DH = Month (DH in MSDOS)
  8790                              <1> 	;		HW of EDX = Year (CX in MSDOS)
  8791                              <1> 	;
  8792                              <1> 	;	For BL input = 1
  8793                              <1> 	;          EAX = Current Time (RTC)
  8794                              <1> 	;		AL = Second (DL in MSDOS)
  8795                              <1> 	;		AH = Minute (CL in MSDOS)
  8796                              <1> 	;	   	HW of EAX = Hour (CH in MSDOS)	
  8797                              <1> 	;
  8798                              <1> 	;	For BL input = 0
  8799                              <1> 	;          EAX = Unix (Epoch) Time Ticks/Seconds
  8800                              <1> 	;
  8801                              <1> 	;	For BL input  = 4
  8802                              <1> 	;	   EAX = System timer ticks
  8803                              <1> 	;
  8804                              <1> 	;	If CF = 1 (for other values of BL input)
  8805                              <1> 	;	   EAX = System timer ticks (no error code!)	
  8806                              <1> 	;		
  8807                              <1> 	; Modified Registers: EAX, (EDX)
  8808                              <1> 	;		 (at the return of system call)
  8809                              <1> 	;
  8810                              <1> 
  8811 0000F964 20DB                <1> 	and	bl, bl
  8812 0000F966 750F                <1> 	jnz	short systime_1
  8813 0000F968 E8FF73FFFF          <1> 	call	epoch
  8814                              <1> systime_0:
  8815 0000F96D A3[64030300]        <1> 	mov	[u.r0], eax
  8816 0000F972 E923D6FFFF          <1> 	jmp	sysret
  8817                              <1> systime_1:
  8818 0000F977 80FB04              <1> 	cmp	bl, 4
  8819 0000F97A 7211                <1> 	jb	short systime_2
  8820 0000F97C A1[005F0100]        <1> 	mov	eax, [TIMER_LH] ; 18.2 Hz timer ticks
  8821                              <1> 				; Note: [TIMER_LH] may be set
  8822                              <1> 				; to wrong timer value due to
  8823                              <1> 				; program functions.
  8824                              <1> 				; (This value must not be
  8825                              <1> 				; accepted as [TIMER_LH]/18.2
  8826                              <1> 				; seconds since the midnight.)
  8827 0000F981 76EA                <1> 	jna	short systime_0
  8828 0000F983 A3[64030300]        <1> 	mov	[u.r0], eax	
  8829 0000F988 E9EDD5FFFF          <1> 	jmp	error ; cf = 1 & [u.r0] = eax = timer ticks 
  8830                              <1> 
  8831                              <1> systime_2:
  8832                              <1> 	;push	ebx
  8833 0000F98D E83C73FFFF          <1> 	call	get_rtc_date_time
  8834                              <1> 	;pop	ebx
  8835 0000F992 F6C301              <1> 	test	bl, 1
  8836 0000F995 7429                <1> 	jz	short systime_4
  8837 0000F997 30E4                <1> 	xor	ah, ah
  8838 0000F999 A0[4A5B0100]        <1> 	mov	al, [hour]
  8839 0000F99E 88C2                <1> 	mov	dl, al
  8840 0000F9A0 C1E010              <1> 	shl	eax, 16
  8841 0000F9A3 A0[4E5B0100]        <1> 	mov	al, [second]
  8842 0000F9A8 8A25[4C5B0100]      <1> 	mov	ah, [minute]
  8843 0000F9AE F6C302              <1> 	test	bl, 2
  8844 0000F9B1 74BA                <1> 	jz	short systime_0
  8845                              <1> 	; Check time & date match risk 
  8846                              <1> 	; (23:59:59 may cause to wrong
  8847                              <1> 	; date -new day with previous date-...)
  8848 0000F9B3 80FA17              <1> 	cmp	dl, 23
  8849 0000F9B6 7206                <1> 	jb	short systime_3
  8850 0000F9B8 663D3B3B            <1> 	cmp	ax, (59*256)+59 ; if hour is 23:59:59
  8851 0000F9BC 73CF                <1> 	jnb	short systime_2 ; wait for 1 second
  8852                              <1> systime_3:
  8853                              <1> 	; eax = time
  8854 0000F9BE 89C6                <1> 	mov	esi, eax
  8855                              <1> systime_4:	
  8856 0000F9C0 66A1[445B0100]      <1> 	mov	ax, [year]
  8857 0000F9C6 C1E010              <1> 	shl	eax, 16
  8858 0000F9C9 A0[485B0100]        <1> 	mov	al, [day]
  8859 0000F9CE 8A25[465B0100]      <1> 	mov	ah, [month]
  8860                              <1> 	; eax = date
  8861 0000F9D4 80E301              <1> 	and	bl, 1
  8862 0000F9D7 7494                <1> 	jz	short systime_0
  8863 0000F9D9 96                  <1> 	xchg	esi, eax
  8864                              <1> 	; eax = time, esi = date
  8865 0000F9DA 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; EBP points to user's registers
  8866                              <1> 	; (user) edx <-- (system) esi
  8867 0000F9E0 897514              <1> 	mov	[ebp+20], esi ; return to user with EDX value 
  8868 0000F9E3 EB88                <1> 	jmp	short systime_0
  8869                              <1> 
  8870                              <1> 
  8871                              <1> sysstime: ; Set System Date&Time
  8872                              <1> 	; 31/12/2017
  8873                              <1> 	; 30/12/2017 (TRDOS 386 = TRDOS v2.0) 
  8874                              <1> 	;	
  8875                              <1>         ; INPUT -> BL =
  8876                              <1> 	;	    0 = Set Date&Time in Unix/Epoch format
  8877                              <1> 	;	    1 = Set Time in MSDOS format
  8878                              <1> 	;	    2 = Set Date in MSDOS format
  8879                              <1> 	;	    3 = Set Date&Time in MSDOS format
  8880                              <1> 	;	    4 = Set System Timer (Ticks)
  8881                              <1> 	;	    5 = Convert/Save current time to/as
  8882                              <1> 	;		18.2 Hz system timer ticks
  8883                              <1> 	;	    6 = Convert MSDOS Date&Time to UNIX format
  8884                              <1> 	;		without setting system date&time ; (test)
  8885                              <1> 	;	    7 = Convert UNIX Date&Time to MSDOS format
  8886                              <1> 	;		without setting system date&time ; (test)
  8887                              <1> 	;	   8-0FFh = invalid !
  8888                              <1> 	;	  ECX = Time (or Timer) value in selected format  	
  8889                              <1> 	;	  EDX = Date value in MSDOS format if BL=2,3,6	
  8890                              <1> 	; 	
  8891                              <1> 	; OUTPUT ->
  8892                              <1> 	;	If CF = 0 ->
  8893                              <1> 	;          EAX = Set value
  8894                              <1> 	;	If CF = 1 -> (invalid BL input)
  8895                              <1> 	;	   EAX = Ticks count [TIMER_LH]	
  8896                              <1> 	;
  8897                              <1> 
  8898 0000F9E5 20DB                <1> 	and	bl, bl ; 0
  8899 0000F9E7 7511                <1> 	jnz	short sysstime_0
  8900 0000F9E9 89C8                <1> 	mov	eax, ecx
  8901 0000F9EB E80674FFFF          <1> 	call	convert_from_epoch
  8902 0000F9F0 E8B274FFFF          <1> 	call	set_rtc_date_time
  8903 0000F9F5 E9A0D5FFFF          <1> 	jmp	sysret
  8904                              <1> sysstime_0:
  8905 0000F9FA 80FB08              <1> 	cmp	bl, 8
  8906 0000F9FD 722D                <1> 	jb	short sysstime_1
  8907                              <1> 	; invalid input (>7)
  8908 0000F9FF A1[005F0100]        <1> 	mov	eax, [TIMER_LH] ; 18.2 Hz timer ticks
  8909                              <1> 				; Note: [TIMER_LH] may be set
  8910                              <1> 				; to wrong timer value due to
  8911                              <1> 				; program functions.
  8912                              <1> 				; (This value must not be
  8913                              <1> 				; accepted as [TIMER_LH]/18.2
  8914                              <1> 				; seconds since the midnight.)
  8915 0000FA04 A3[64030300]        <1> 	mov	[u.r0], eax	
  8916 0000FA09 E96CD5FFFF          <1> 	jmp	error ; cf = 1 & [u.r0] = eax = timer ticks 
  8917                              <1> 
  8918                              <1> sysstime_8:	
  8919                              <1> 	; BL = 7
  8920 0000FA0E 89C8                <1> 	mov	eax, ecx ; seconds since 1/1/1970 00:00:00
  8921 0000FA10 E8E173FFFF          <1> 	call	convert_from_epoch
  8922 0000FA15 30E4                <1> 	xor	ah, ah
  8923 0000FA17 A0[4A5B0100]        <1> 	mov	al, [hour]
  8924 0000FA1C C1E010              <1> 	shl	eax, 16
  8925 0000FA1F A0[4E5B0100]        <1> 	mov	al, [second]
  8926 0000FA24 8A25[4C5B0100]      <1> 	mov	ah, [minute]
  8927 0000FA2A EB92                <1> 	jmp	short systime_3
  8928                              <1> 
  8929                              <1> sysstime_1:
  8930 0000FA2C 80FB04              <1> 	cmp	bl, 4
  8931 0000FA2F 743F                <1> 	je	short sysstime_2 ; set system timer ticks	
  8932 0000FA31 80FB05              <1> 	cmp	bl, 5
  8933 0000FA34 754B                <1> 	jne	short sysstime_4
  8934                              <1> 	; convert current time to system timer ticks (18.2Hz)
  8935 0000FA36 E89372FFFF          <1> 	call	get_rtc_date_time
  8936 0000FA3B 0FB60D[4A5B0100]    <1> 	movzx	ecx, byte [hour]
  8937 0000FA42 B8100E0000          <1> 	mov	eax, 60*60 ; 1 hour = 3600 seconds
  8938 0000FA47 F7E1                <1> 	mul	ecx
  8939 0000FA49 89C3                <1> 	mov	ebx, eax	
  8940 0000FA4B B13C                <1> 	mov	cl, 60  ; 1 minute = 60 seconds
  8941 0000FA4D 0FB605[4C5B0100]    <1> 	movzx	eax, byte [minute]
  8942 0000FA54 F7E1                <1> 	mul	ecx
  8943 0000FA56 01D8                <1> 	add	eax, ebx  
  8944 0000FA58 8A0D[4E5B0100]      <1> 	mov	cl, [second]
  8945 0000FA5E 01C8                <1> 	add	eax, ecx
  8946 0000FA60 B1B6                <1> 	mov	cl, 182
  8947 0000FA62 F7E1                <1> 	mul	ecx
  8948 0000FA64 83C009              <1> 	add	eax, 9
  8949 0000FA67 83D200              <1> 	adc	edx, 0
  8950 0000FA6A B10A                <1> 	mov	cl, 10
  8951 0000FA6C F7F1                <1> 	div	ecx
  8952                              <1> 	; eax = ((182*seconds)+9)/10
  8953 0000FA6E 89C1                <1> 	mov	ecx, eax
  8954                              <1> sysstime_2:
  8955 0000FA70 890D[005F0100]      <1> 	mov	[TIMER_LH], ecx ; 18.2 * seconds
  8956                              <1> sysstime_3:
  8957 0000FA76 890D[64030300]      <1> 	mov	[u.r0], ecx
  8958 0000FA7C E919D5FFFF          <1> 	jmp	sysret
  8959                              <1> sysstime_4:
  8960 0000FA81 80FB06              <1> 	cmp	bl, 6
  8961 0000FA84 7788                <1> 	ja	short sysstime_8
  8962                              <1> 
  8963 0000FA86 890D[64030300]      <1> 	mov	[u.r0], ecx
  8964                              <1> 
  8965 0000FA8C 880D[4E5B0100]      <1> 	mov	[second], cl
  8966 0000FA92 882D[4C5B0100]      <1> 	mov	[minute], ch
  8967 0000FA98 C1E910              <1> 	shr	ecx, 16
  8968 0000FA9B 880D[4A5B0100]      <1> 	mov	[hour], cl
  8969                              <1> 	; BL = 1,2,3,6
  8970 0000FAA1 80FB01              <1> 	cmp	bl, 1
  8971 0000FAA4 762A                <1> 	jna	short sysstime_5
  8972                              <1> 	; BL = 2,3,6
  8973 0000FAA6 8815[485B0100]      <1> 	mov	[day], dl
  8974 0000FAAC 8835[465B0100]      <1> 	mov	[month], dh
  8975 0000FAB2 C1EA10              <1> 	shr	edx, 16
  8976 0000FAB5 668915[445B0100]    <1> 	mov	[year], dx
  8977 0000FABC 80E303              <1> 	and	bl, 3
  8978 0000FABF 742D                <1> 	jz	short sysstime_7 ; 6
  8979                              <1> 	; BL = 2,3
  8980 0000FAC1 F6C301              <1> 	test	bl, 1
  8981 0000FAC4 7419                <1> 	jz	short sysstime_6 ; 2
  8982                              <1> 	; BL = 3
  8983 0000FAC6 E8DC73FFFF          <1> 	call	set_rtc_date_time
  8984 0000FACB E9CAD4FFFF          <1> 	jmp	sysret
  8985                              <1> sysstime_5:
  8986                              <1> 	; BL = 1
  8987 0000FAD0 E81374FFFF          <1> 	call	set_time_bcd
  8988 0000FAD5 E8AE66FFFF          <1> 	call	set_rtc_time
  8989 0000FADA E9BBD4FFFF          <1> 	jmp	sysret	
  8990                              <1> sysstime_6:
  8991                              <1> 	; BL = 2
  8992 0000FADF E8D773FFFF          <1> 	call	set_date_bcd
  8993 0000FAE4 E80E67FFFF          <1> 	call	set_rtc_date
  8994 0000FAE9 E9ACD4FFFF          <1> 	jmp	sysret
  8995                              <1> sysstime_7:
  8996                              <1> 	; BL = 6
  8997                              <1> 	; [year], [month], [day], 
  8998                              <1> 	; [hour], [minute], [second]
  8999 0000FAEE E87E72FFFF          <1> 	call	convert_to_epoch
  9000 0000FAF3 89C1                <1> 	mov	ecx, eax ; seconds since 1/1/1970 00:00:00
  9001 0000FAF5 E97CFFFFFF          <1> 	jmp	sysstime_3
  9002                              <1> 
  9003                              <1> sysrename: ; Rename File (or Directory)
  9004                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0) 
  9005                              <1> 	;	
  9006                              <1>         ; INPUT ->
  9007                              <1>         ;          EBX = File/Directory (ASCIIZ) name address
  9008                              <1> 	;	   ECX = New name (in same dir, no path name)			
  9009                              <1> 	; OUTPUT ->
  9010                              <1> 	;          cf = 0 -> EAX = 0
  9011                              <1> 	;          cf = 1 -> Error code in AL
  9012                              <1> 
  9013 0000FAFA 803D[B3030300]00    <1> 	cmp	byte [u.uno], 0  ; root (super user) ?
  9014 0000FB01 7614                <1> 	jna	short sysrename_0
  9015                              <1> 
  9016                              <1> sysrename_perm_err:
  9017                              <1> 	;mov	dword [u.r0], ERR_PERM_DENIED
  9018 0000FB03 B80B000000          <1> 	mov	eax, ERR_PERM_DENIED ; 'permission denied !'
  9019 0000FB08 A3[64030300]        <1> 	mov	[u.r0], eax
  9020 0000FB0D A3[C8030300]        <1> 	mov	[u.error], eax
  9021 0000FB12 E963D4FFFF          <1> 	jmp	error
  9022                              <1> 
  9023                              <1> sysrename_0:
  9024 0000FB17 51                  <1> 	push	ecx ; new file name address (in user space)
  9025 0000FB18 89DE                <1> 	mov	esi, ebx
  9026                              <1> 	; file name is forced, change directory as temporary
  9027                              <1> 	;mov	ax, 1
  9028                              <1> 	;mov	[FFF_Valid], ah ; 0 ; reset
  9029                              <1> 	;call	set_working_path 
  9030 0000FB1A E8C5060000          <1> 	call	set_working_path_x
  9031 0000FB1F 731E                <1> 	jnc	short sysrename_1
  9032 0000FB21 21C0                <1> 	and	eax, eax  ; 0 -> Bad Path!  
  9033 0000FB23 7505                <1> 	jnz	short sysrename_err
  9034                              <1> 	; eax = 0
  9035                              <1> sysrename_path_not_found:
  9036 0000FB25 B813000000          <1> 	mov	eax, ERR_INV_PATH_NAME ; 'Bad path name !'
  9037                              <1> sysrename_err:
  9038 0000FB2A 59                  <1> 	pop	ecx ; new file name address (in user space)
  9039                              <1> sysrename_error:
  9040 0000FB2B A3[64030300]        <1> 	mov	[u.r0], eax
  9041 0000FB30 A3[C8030300]        <1> 	mov	[u.error], eax
  9042 0000FB35 E87F070000          <1> 	call 	reset_working_path
  9043 0000FB3A E93BD4FFFF          <1> 	jmp	error
  9044                              <1> sysrename_1:
  9045 0000FB3F B008                <1> 	mov	al, 08h ; Except volume labels (& long names)
  9046 0000FB41 A0[FC680100]        <1> 	mov	al, [Attributes]
  9047 0000FB46 2410                <1> 	and	al, 10h ;
  9048                              <1> 	;mov	esi, FindFile_Name
  9049                              <1> 	;mov	ax, 1800h ; Only files
  9050                              <1> 	;mov	ax, 0810h ; Only directories
  9051 0000FB48 66B80008            <1> 	mov	ax, 0800h ; Find File or Directory
  9052 0000FB4C E8CE8FFFFF          <1> 	call	find_first_file
  9053                              <1> 	;jnc	short sysrename_2
  9054 0000FB51 72D7                <1> 	jc	short sysrename_err
  9055                              <1> sysrename_2:
  9056                              <1> 	; ESI = Directory Entry (FindFile_DirEntry) Location
  9057                              <1> 	; EDI = Directory Buffer Directory Entry Location
  9058                              <1> 	; EAX = File Size
  9059                              <1> 	;  BL = Attributes of The File/Directory
  9060                              <1> 	;  BH = Long Name Yes/No Status (>0 is YES)
  9061                              <1> 	;  DX > 0 : Ambiguous filename chars are used
  9062                              <1> 
  9063 0000FB53 6621D2              <1> 	and	dx, dx ; Ambiguous filename chars used sign (DX>0)
  9064 0000FB56 7407                <1> 	jz	short sysrename_3
  9065 0000FB58 B81A000000          <1> 	mov	eax, ERR_INV_FILE_NAME ; 'invalid file name !'
  9066 0000FB5D EBCB                <1>         jmp	short sysrename_err
  9067                              <1> sysrename_3:
  9068                              <1> 	; EDI = Directory buffer entry offset/address
  9069                              <1> 	; BL = File (or Directory) Attributes 
  9070                              <1> 	; mov	bl, [EDI+0Bh]
  9071                              <1> 
  9072 0000FB5F 5A                  <1> 	pop	edx ; new file name address (in user space)
  9073                              <1> 
  9074                              <1> 	; check file/directory attributes
  9075 0000FB60 F6C307              <1> 	test	bl, 7 ; system, hidden, readonly 
  9076 0000FB63 759E                <1>         jnz	short sysrename_perm_err
  9077                              <1> sysrename_4:
  9078 0000FB65 66817F0CA101        <1> 	cmp	word [edi+DirEntry_NTRes], 01A1h ; Singlix FS
  9079 0000FB6B 7496                <1> 	je	short sysrename_perm_err ; -temporary!-
  9080                              <1> 
  9081                              <1> 	; save old file name & file info (FFF structure)
  9082 0000FB6D BE[E6670100]        <1> 	mov	esi, FindFile_Drv
  9083 0000FB72 BF[2C690100]        <1> 	mov	edi, SourceFile_Drv
  9084 0000FB77 B920000000          <1> 	mov	ecx, 128/4
  9085 0000FB7C F3A5                <1> 	rep	movsd
  9086                              <1> 
  9087 0000FB7E 89D6                <1> 	mov	esi, edx ; new file name address (in user space)
  9088 0000FB80 BF[AC690100]        <1> 	mov	edi, DestinationFile_Drv
  9089 0000FB85 E866B1FFFF          <1> 	call	parse_path_name
  9090 0000FB8A 729F                <1> 	jc	short sysrename_error ; eax = 1 (Bad file name)
  9091                              <1> 
  9092                              <1> 	; same drive ? 
  9093 0000FB8C A0[E6670100]        <1> 	mov	al, [FindFile_Drv]
  9094 0000FB91 3A05[AC690100]      <1> 	cmp	al, [DestinationFile_Drv]
  9095                              <1> 	;jne	short sysrename_perm_err ; Permission denied
  9096 0000FB97 7509                <1> 	jne	short sysrename_5 ; Bad file name
  9097                              <1>  
  9098                              <1> 	; no path name !? (rename file in same directory)
  9099 0000FB99 803D[AD690100]20    <1> 	cmp	byte [DestinationFile_Directory], 20h
  9100 0000FBA0 7607                <1> 	jna	short sysrename_6
  9101                              <1> sysrename_5:
  9102 0000FBA2 B801000000          <1> 	mov	eax, ERR_BAD_CMD_ARG ; 1 = Bad file name 
  9103                              <1> 				     ; (Bad argument)
  9104 0000FBA7 EB82                <1> 	jmp	short sysrename_error
  9105                              <1> sysrename_6:
  9106 0000FBA9 803D[EE690100]20    <1> 	cmp	byte [DestinationFile_Name], 20h
  9107 0000FBB0 76F0                <1> 	jna	short sysrename_5
  9108                              <1> 
  9109 0000FBB2 BE[EE690100]        <1> 	mov	esi, DestinationFile_Name
  9110 0000FBB7 E82193FFFF          <1> 	call	check_filename ; is it a valid msdos file name?
  9111 0000FBBC 0F8269FFFFFF        <1> 	jc	sysrename_error ; 26 = ERR_INV_FILE_NAME 
  9112                              <1> 	
  9113                              <1> 	;mov	esi, DestinationFile_Name
  9114 0000FBC2 66B80008            <1> 	mov	ax, 0800h ; Find File or Directory
  9115 0000FBC6 E8548FFFFF          <1> 	call	find_first_file
  9116 0000FBCB 720A                <1> 	jc	short sysrename_7
  9117                              <1> 	
  9118 0000FBCD B80E000000          <1> 	mov	eax, ERR_FILE_EXISTS  ; file already exists !
  9119 0000FBD2 E954FFFFFF          <1> 	jmp	sysrename_error	
  9120                              <1> sysrename_7:
  9121                              <1> 	; eax = 2 (File not found !)
  9122 0000FBD7 3C02                <1> 	cmp	al, 2 ; ERR_NOT_FOUND
  9123 0000FBD9 0F854CFFFFFF        <1> 	jne	sysrename_error
  9124                              <1> 
  9125                              <1> 	; 31/12/2017
  9126                              <1> 	; Following code is also part of 'rename_file' in
  9127                              <1> 	; 'trdosk3.s' (MainProg's 'rename' command) ; 13/11/2017
  9128 0000FBDF BE[EE690100]        <1> 	mov	esi, DestinationFile_Name ; (Rename_NewName)
  9129 0000FBE4 668B0D[A6690100]    <1> 	mov	cx, [SourceFile_DirEntryNumber] 
  9130 0000FBEB 66A1[92690100]      <1> 	mov	ax, [SourceFile_DirEntry+20] ; First Cluster, HW 
  9131 0000FBF1 C1E010              <1> 	shl	eax, 16
  9132 0000FBF4 66A1[98690100]      <1> 	mov	ax, [SourceFile_DirEntry+26] ; First Cluster, LW 
  9133 0000FBFA 0FB61D[7B690100]    <1>   	movzx	ebx, byte [SourceFile_LongNameEntryLength]  
  9134 0000FC01 E832B9FFFF          <1>    	call	rename_directory_entry
  9135 0000FC06 0F821FFFFFFF        <1> 	jc	sysrename_error
  9136                              <1> 	;xor	eax, eax
  9137 0000FC0C A3[64030300]        <1> 	mov	[u.r0], eax ; 0
  9138                              <1> 	;mov	[u.error], eax
  9139 0000FC11 E8A3060000          <1> 	call 	reset_working_path
  9140 0000FC16 E97FD3FFFF          <1> 	jmp	sysret
  9141                              <1> 
  9142                              <1> sysmem: ; Get Total&Free Memory amount 
  9143                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0) 
  9144                              <1> 	;	
  9145                              <1>         ; INPUT -> 
  9146                              <1> 	;	none	
  9147                              <1> 	; OUTPUT ->
  9148                              <1> 	;	EAX = Total memory count (in bytes)
  9149                              <1> 	;	EBX = Virtually available memory amount (in bytes)
  9150                              <1> 	;	      = 4GB - CORE (4MB)	
  9151                              <1> 	;	ECX = Free memory count (in bytes)
  9152                              <1> 	;	EDX = Calculated free memory count (in bytes)
  9153                              <1> 	
  9154 0000FC1B A1[845E0100]        <1> 	mov	eax, [memory_size] ; in pages
  9155 0000FC20 C1E00C              <1> 	shl	eax, 12		   ; in bytes
  9156 0000FC23 A3[64030300]        <1> 	mov	[u.r0], eax
  9157 0000FC28 E8323EFFFF          <1> 	call	calc_free_mem
  9158                              <1> 	; edx = calculated free pages
  9159                              <1> 	; ecx = 0
  9160 0000FC2D 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; EBP points to user's registers
  9161 0000FC33 C745100000C0FF      <1> 	mov	dword [ebp+16], ECORE ; EBX (for user)
  9162                              <1> 				; 0FFC00000h ; 4GB - 4MB
  9163 0000FC3A C1E20C              <1> 	shl	edx, 12
  9164 0000FC3D 895514              <1> 	mov	[ebp+20], edx ; EDX (for user)
  9165 0000FC40 8B0D[885E0100]      <1> 	mov 	ecx, [free_pages]
  9166 0000FC46 C1E10C              <1> 	shl	ecx, 12	; free bytes
  9167 0000FC49 894D18              <1> 	mov	[ebp+24], ecx ; ECX (for user)
  9168                              <1> 	;mov	[free_pages], edx	
  9169 0000FC4C E949D3FFFF          <1> 	jmp	sysret
  9170                              <1> 
  9171                              <1> sysprompt:
  9172                              <1> 	; Set TRDOS 386 Command Interpreter (MainProg) prompt 
  9173                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0) 
  9174                              <1> 	;	
  9175                              <1>         ; INPUT -> 
  9176                              <1> 	;	EBX = 0 -> use default prompt
  9177                              <1> 	;	EBX > 0 -> prompt string (ASCIIZ) address
  9178                              <1> 	;		  (Max. 11 characters except ZERO tail)	
  9179                              <1> 	; OUTPUT ->
  9180                              <1> 	;	(EAX = 0)
  9181                              <1> 	;	CF = 0 -> Successful
  9182                              <1> 	;	CF = 1 -> Failed
  9183                              <1> 
  9184 0000FC51 21DB                <1> 	and	ebx, ebx
  9185 0000FC53 750A                <1> 	jnz	short sysprompt_0
  9186                              <1> 
  9187 0000FC55 E8C988FFFF          <1> 	call	default_command_prompt ; '['+'TRDOS'+']'
  9188 0000FC5A E93BD3FFFF          <1> 	jmp	sysret
  9189                              <1> 
  9190                              <1> sysprompt_0:
  9191 0000FC5F 31C0                <1> 	xor	eax, eax
  9192 0000FC61 A3[64030300]        <1> 	mov	[u.r0], eax 
  9193 0000FC66 89DE                <1> 	mov	esi, ebx
  9194 0000FC68 B90C000000          <1> 	mov	ecx, 12
  9195 0000FC6D 89E5                <1> 	mov	ebp, esp
  9196 0000FC6F 29CC                <1> 	sub	esp, ecx
  9197 0000FC71 49                  <1> 	dec	ecx ; 11
  9198 0000FC72 89E7                <1> 	mov	edi, esp
  9199 0000FC74 E833F1FFFF          <1> 	call	transfer_from_user_buffer
  9200 0000FC79 7211                <1> 	jc	short sysprompt_err
  9201 0000FC7B 803E20              <1> 	cmp	byte [esi], 20h
  9202 0000FC7E 760C                <1> 	jna	short sysprompt_err
  9203 0000FC80 E8B088FFFF          <1> 	call	set_command_prompt
  9204 0000FC85 89EC                <1> 	mov	esp, ebp
  9205 0000FC87 E90ED3FFFF          <1> 	jmp	sysret
  9206                              <1> sysprompt_err:
  9207                              <1> syspath_err:
  9208 0000FC8C 89EC                <1> 	mov	esp, ebp
  9209 0000FC8E E9E7D2FFFF          <1> 	jmp	error
  9210                              <1> 
  9211                              <1> syspath:
  9212                              <1> 	; Get/Set Run Path
  9213                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0) 
  9214                              <1> 	;	
  9215                              <1>         ; INPUT -> 
  9216                              <1> 	;	EBX = 0 -> get path (to buffer address in ECX)
  9217                              <1> 	;	EBX > 0 -> set path
  9218                              <1> 	;	    EBX = Path string buffer address (ASCIIZ)
  9219                              <1> 	;	    	  (Path description except 'PATH=')
  9220                              <1> 	;	ECX = Buffer address (if EBX = 0)
  9221                              <1> 	;	      (ECX will not be used if EBX > 0)	
  9222                              <1> 	;	DL = Buffer size (0 = 256 byte)	
  9223                              <1> 	;
  9224                              <1> 	; OUTPUT ->
  9225                              <1> 	;	CF = 0 -> Successful (EAX = String length)
  9226                              <1> 	;	CF = 1 -> Failed (EAX = 0)
  9227                              <1> 	;
  9228                              <1> 	; NOTE: 'PATH=' or 'PATH' must be excluded
  9229                              <1> 	;  (It must not be at the beginning of the string.)
  9230                              <1> 
  9231 0000FC93 89E5                <1> 	mov	ebp, esp
  9232 0000FC95 81EC00010000        <1> 	sub	esp, 256
  9233 0000FC9B 89E7                <1> 	mov	edi, esp
  9234                              <1> 
  9235 0000FC9D 31C0                <1> 	xor	eax, eax
  9236 0000FC9F A3[64030300]        <1> 	mov	[u.r0], eax 
  9237                              <1> 	
  9238 0000FCA4 21DB                <1> 	and	ebx, ebx
  9239 0000FCA6 752E                <1> 	jnz	short syspath_0
  9240                              <1> 
  9241                              <1> 	; EBX = 0 -> get run path
  9242 0000FCA8 89CB                <1> 	mov	ebx, ecx ; buffer addr (in user's mem space)
  9243 0000FCAA BE[93130100]        <1> 	mov	esi, Cmd_Path  ; 'PATH' address
  9244 0000FCAF 0FB6CA              <1> 	movzx	ecx, dl
  9245 0000FCB2 80E901              <1> 	sub	cl, 1 ; 0 -> 255, 1 -> 0
  9246 0000FCB5 6683D101            <1> 	adc	cx, 1 ; 255 -> 256, 0 -> 1
  9247                              <1> 	; EDI = Output buffer 
  9248                              <1> 	; CX = Buffer length
  9249                              <1> 	; AL = 0 -> use ASCIIZ word in [ESI]
  9250                              <1> 	; ESI = 'PATH' address (with zero tail)
  9251 0000FCB9 E8ABA0FFFF          <1> 	call	get_environment_string
  9252 0000FCBE 72CC                <1> 	jc	short syspath_err
  9253 0000FCC0 89DF                <1> 	mov	edi, ebx ; User's buffer address
  9254 0000FCC2 89E6                <1> 	mov	esi, esp 
  9255                              <1> 	; EDI = User's buffer address
  9256                              <1> 	; ECX = transfer (byte) count
  9257 0000FCC4 E899F0FFFF          <1> 	call	transfer_to_user_buffer
  9258 0000FCC9 72C1                <1> 	jc	short syspath_err
  9259 0000FCCB 890D[64030300]      <1> 	mov	[u.r0], ecx 
  9260 0000FCD1 E9C4D2FFFF          <1> 	jmp	sysret
  9261                              <1> 
  9262                              <1> syspath_0:
  9263 0000FCD6 89DE                <1> 	mov	esi, ebx
  9264 0000FCD8 0FB6CA              <1> 	movzx	ecx, dl
  9265 0000FCDB 80E901              <1> 	sub	cl, 1 ; 0 -> 255, 1 -> 0
  9266 0000FCDE 6683D101            <1> 	adc	cx, 1 ; 255 -> 256, 0 -> 1
  9267 0000FCE2 E8C5F0FFFF          <1> 	call	transfer_from_user_buffer
  9268 0000FCE7 72A3                <1> 	jc	short syspath_err
  9269                              <1> 	;(*) 'PATH=' will be added to 
  9270                              <1> 	;         the head of the string
  9271 0000FCE9 83EC08              <1> 	sub	esp, 8 ;(*)
  9272 0000FCEC 89FE                <1> 	mov	esi, edi ;(*)
  9273 0000FCEE E85AA0FFFF          <1> 	call	set_path_x ;(*)
  9274 0000FCF3 7297                <1> 	jc	short syspath_err
  9275 0000FCF5 8915[64030300]      <1> 	mov	[u.r0], edx ; run path string length
  9276 0000FCFB E99AD2FFFF          <1> 	jmp	sysret	
  9277                              <1> 
  9278                              <1> sysenv:
  9279                              <1> 	; Get/Set Environment Variables
  9280                              <1> 	; 31/12/2017 (TRDOS 386 = TRDOS v2.0) 
  9281                              <1> 	;	
  9282                              <1>         ; INPUT -> 
  9283                              <1> 	;	EBX = 0 -> get (all) environment variables
  9284                              <1> 	;	      (Required Buffer length = 512 bytes)
  9285                              <1> 	;	EBX > 0 -> set (one) environment variable
  9286                              <1> 	;	      (If there is not a '=' after
  9287                              <1> 	;	      the environment variable name, it will
  9288                              <1> 	;	      accepted as 'get environment variable'.) 
  9289                              <1> 	;	       EBX = Buffer address
  9290                              <1> 	;	ECX = Buffer address (if EBX = 0)
  9291                              <1> 	;	      (ECX will not be used if EBX > 0)	
  9292                              <1> 	;	      (Note: Buffer size is 512 bytes.)	
  9293                              <1> 	;	DL = Buffer size (0 = 256 byte)
  9294                              <1> 	;	     (For one envrionment variable)		
  9295                              <1> 	;
  9296                              <1> 	; OUTPUT ->
  9297                              <1> 	;	(EAX = 0)
  9298                              <1> 	;	CF = 0 -> Successful (EAX = String length)
  9299                              <1> 	;	CF = 1 -> Failed (EAX = 0)
  9300                              <1> 	;
  9301                              <1> 	; Note: Environment variable name, for example,
  9302                              <1> 	;	'PATH=' must be included at the beginning
  9303                              <1> 	;	of the environment string. If the variable
  9304                              <1> 	;	name is as 'PATH' but it is not as 'PATH='
  9305                              <1> 	;	the variable string (row) will be returned.
  9306                              <1> 	;	If variable name is as 'PATH=' but there is
  9307                              <1> 	;	not a following text after the variable name,
  9308                              <1> 	;	the environment variable will be reset/deleted.
  9309                              <1> 
  9310 0000FD00 89E5                <1> 	mov	ebp, esp
  9311 0000FD02 81EC00020000        <1> 	sub	esp, 512
  9312 0000FD08 89E7                <1> 	mov	edi, esp
  9313                              <1> 
  9314 0000FD0A 31C0                <1> 	xor	eax, eax
  9315 0000FD0C A3[64030300]        <1> 	mov	[u.r0], eax 
  9316                              <1> 	
  9317 0000FD11 21DB                <1> 	and	ebx, ebx
  9318 0000FD13 7524                <1> 	jnz	short sysenv_0
  9319                              <1> 
  9320                              <1> 	; EBX = 0 -> get (all) environment variables
  9321 0000FD15 89EC                <1> 	mov	esp, ebp
  9322 0000FD17 BE00300900          <1> 	mov	esi, Env_Page  ; Environment page
  9323 0000FD1C 89CF                <1> 	mov	edi, ecx ; buffer addr (in user's mem space)
  9324 0000FD1E B900020000          <1> 	mov	ecx, 512
  9325 0000FD23 E83AF0FFFF          <1> 	call	transfer_to_user_buffer
  9326 0000FD28 0F824CD2FFFF        <1> 	jc	error
  9327 0000FD2E 890D[64030300]      <1> 	mov	[u.r0], ecx 
  9328 0000FD34 E961D2FFFF          <1> 	jmp	sysret
  9329                              <1> 
  9330                              <1> sysenv_0:
  9331 0000FD39 89DE                <1> 	mov	esi, ebx ; * ; user's buffer address
  9332 0000FD3B 0FB6CA              <1> 	movzx	ecx, dl
  9333 0000FD3E 80E901              <1> 	sub	cl, 1 ; 0 -> 255, 1 -> 0
  9334 0000FD41 6683D101            <1> 	adc	cx, 1 ; 255 -> 256, 0 -> 1
  9335 0000FD45 E862F0FFFF          <1> 	call	transfer_from_user_buffer
  9336 0000FD4A 723F                <1> 	jc	short sysenv_err
  9337 0000FD4C 89FE                <1> 	mov	esi, edi
  9338 0000FD4E 8A06                <1> 	mov	al, [esi]
  9339 0000FD50 3C20                <1> 	cmp	al, 20h
  9340 0000FD52 7637                <1> 	jna	short sysenv_err
  9341 0000FD54 3C3D                <1> 	cmp	al, '='
  9342 0000FD56 7433                <1> 	je	short sysenv_err
  9343 0000FD58 56                  <1> 	push	esi
  9344                              <1> sysenv_1:
  9345 0000FD59 46                  <1> 	inc	esi
  9346 0000FD5A 803E3D              <1> 	cmp	byte [esi], '='
  9347 0000FD5D 7433                <1> 	je	short sysenv_3
  9348 0000FD5F 803E20              <1> 	cmp	byte [esi], 20h
  9349 0000FD62 73F5                <1> 	jnb	short sysenv_1
  9350 0000FD64 C60600              <1> 	mov	byte [esi], 0 
  9351 0000FD67 5E                  <1> 	pop	esi
  9352                              <1> 	; EDI = Output buffer 
  9353                              <1> 	; CX = Buffer length
  9354 0000FD68 30C0                <1> 	xor	al, al
  9355                              <1> 	; AL = 0 -> use ASCIIZ word in [ESI]
  9356                              <1> 	; ESI = Environment variable name address
  9357 0000FD6A E8FA9FFFFF          <1> 	call	get_environment_string
  9358 0000FD6F 721A                <1> 	jc	short sysenv_err
  9359 0000FD71 89DF                <1> 	mov	edi, ebx ; * ; user's buffer address
  9360 0000FD73 89C1                <1> 	mov	ecx, eax ; String length
  9361 0000FD75 89E6                <1> 	mov	esi, esp 
  9362                              <1> 	; ESI = system buffer address
  9363                              <1> 	; EDI = User's buffer address
  9364                              <1> 	; ECX = transfer (byte) count
  9365 0000FD77 E8E6EFFFFF          <1> 	call	transfer_to_user_buffer
  9366 0000FD7C 720D                <1> 	jc	short sysenv_err
  9367 0000FD7E 890D[64030300]      <1> 	mov	[u.r0], ecx ; transfer (byte) count
  9368                              <1> sysenv_2:
  9369 0000FD84 89EC                <1> 	mov	esp, ebp
  9370 0000FD86 E90FD2FFFF          <1> 	jmp	sysret
  9371                              <1> sysenv_err:
  9372 0000FD8B 89EC                <1> 	mov	esp, ebp
  9373 0000FD8D E9E8D1FFFF          <1> 	jmp	error
  9374                              <1> sysenv_3:
  9375 0000FD92 46                  <1> 	inc	esi
  9376 0000FD93 803E20              <1> 	cmp	byte [esi], 20h
  9377 0000FD96 73FA                <1> 	jnb	short sysenv_3
  9378 0000FD98 C60600              <1> 	mov	byte [esi], 0	
  9379 0000FD9B 5E                  <1> 	pop	esi
  9380 0000FD9C E88BA0FFFF          <1> 	call	set_environment_string
  9381 0000FDA1 72E8                <1> 	jc	short sysenv_err
  9382 0000FDA3 8915[64030300]      <1> 	mov	[u.r0], edx
  9383 0000FDA9 EBD9                <1> 	jmp	short sysenv_2
  9384                              <1> 
  9385                              <1> 
  9386                              <1> ; temporary - 24/01/2016
  9387                              <1> 
  9388                              <1> iget:
  9389 0000FDAB C3                  <1> 	retn
  9390                              <1> isintr:
  9391 0000FDAC C3                  <1> 	retn
  9392                              <1> iopen:
  9393 0000FDAD C3                  <1> 	retn
  9394                              <1> iclose:
  9395 0000FDAE C3                  <1> 	retn
  9396                              <1> sndc:
  9397 0000FDAF C3                  <1> 	retn
  9398                              <1> access:
  9399 0000FDB0 C3                  <1> 	retn
  9400                              <1> sleep:
  9401 0000FDB1 C3                  <1> 	retn
  2867                                  %include 'trdosk7.s' ; 24/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - DISK READ&WRITE : trdosk7.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 25/02/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; DISK_IO.ASM (20/07/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; DISK_IO.ASM (c) 2009-2011 Erdogan TAN [ 04/07/2009 ] Last Update: 20/07/2011
    14                              <1> 
    15                              <1> disk_write:
    16                              <1> 	; 25/02/2016
    17                              <1> 	; 24/02/2016
    18                              <1> 	; 23/02/2016
    19 0000FDB2 807E0500            <1> 	cmp	byte [esi+LD_LBAYes], 0
    20 0000FDB6 777B                <1>         ja      short lba_write
    21                              <1> 
    22                              <1> chs_write:
    23                              <1> 	; 25/02/2016
    24                              <1> 	; 23/02/2016
    25 0000FDB8 C605[35670100]03    <1> 	mov	byte [disk_rw_op], 3 ; CHS write
    26 0000FDBF EB0D                <1> 	jmp	short chs_rw
    27                              <1> 
    28                              <1> disk_read:
    29                              <1> 	; 25/02/2016
    30                              <1> 	; 24/02/2016
    31                              <1> 	; 23/02/2016
    32                              <1> 	; 17/02/2016
    33                              <1> 	; 14/02/2016
    34                              <1> 	; 31/01/2016 (TRDOS 386 =  TRDOS v2.0)
    35                              <1> 	; 17/10/2010
    36                              <1> 	; 18/04/2010
    37                              <1> 	;
    38                              <1> 	; INPUT -> EAX = Logical Block Address
    39                              <1> 	;	   ESI = Logical Dos Disk Table Offset (DRV)	
    40                              <1> 	;	   ECX = Sector Count	
    41                              <1> 	; 	   EBX = Destination Buffer
    42                              <1> 	; OUTPUT -> 
    43                              <1> 	;	   cf = 0 or cf = 1
    44                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX)
    45                              <1> 
    46 0000FDC1 807E0500            <1> 	cmp	byte [esi+LD_LBAYes], 0
    47 0000FDC5 7775                <1>         ja      short lba_read
    48                              <1> 
    49                              <1> chs_read:
    50                              <1> 	; 25/02/2016
    51                              <1> 	; 24/02/2016
    52                              <1> 	; 23/02/2016
    53                              <1> 	; 31/01/2016 (TRDOS 386 =  TRDOS v2.0)
    54                              <1> 	; 20/07/2011
    55                              <1> 	; 04/07/2009
    56                              <1> 	;
    57                              <1> 	; INPUT -> EAX = Logical Block Address
    58                              <1> 	;	   ECX = Number of sectors to read
    59                              <1> 	; 	   ESI = Logical Dos Disk Table Offset (DRV)
    60                              <1> 	; 	   EBX = Destination Buffer
    61                              <1> 	; OUTPUT -> 
    62                              <1> 	;	   cf = 0 or cf = 1
    63                              <1> 	; (Modified registers: EAX; EBX, ECX, EDX)
    64                              <1> 
    65                              <1> 	; 23/02/2016
    66 0000FDC7 C605[35670100]02    <1> 	mov	byte [disk_rw_op], 2 ; CHS read
    67                              <1> 
    68                              <1> chs_rw:
    69                              <1> 	;;movzx	edx, word [esi+LD_BPB+SecPerTrack]
    70                              <1> 	;movzx	edx, byte [esi+LD_BPB+SecPerTrack] ; <= 63
    71                              <1> 	;mov	[disk_rw_spt], dl
    72                              <1> 
    73                              <1> chs_read_next_sector:
    74 0000FDCE C605[36670100]04    <1> 	mov	byte [retry_count], 4
    75                              <1>      
    76                              <1> chs_read_retry:
    77                              <1> 	;mov	[sector_count], ecx ; 23/02/2016
    78                              <1> 
    79 0000FDD5 50                  <1> 	push	eax			; Linear sector #
    80 0000FDD6 51                  <1> 	push	ecx			; # of FAT/FILE/DIR sectors
    81                              <1>                 
    82 0000FDD7 0FB74E1E            <1> 	movzx	ecx, word [esi+LD_BPB+SecPerTrack]
    83                              <1> 	;movzx	ecx, byte [disk_rw_spt] ; 23/02/2016
    84 0000FDDB 29D2                <1> 	sub	edx, edx
    85 0000FDDD F7F1                <1> 	div	ecx
    86                              <1> 	; eax = track, dx (dl ) = sector (on track)
    87                              <1> 	;sub	cl, dl ; 24/02/2016 (spt - sec)
    88                              <1> 	;push	ecx ; *
    89 0000FDDF 6689D1              <1> 	mov	cx, dx			; Sector (zero based)
    90 0000FDE2 6641                <1> 	inc	cx			; To make it 1 based
    91 0000FDE4 6651                <1> 	push	cx
    92 0000FDE6 668B4E20            <1> 	mov	cx, [esi+LD_BPB+Heads]
    93 0000FDEA 6629D2              <1> 	sub	dx, dx
    94 0000FDED F7F1                <1> 	div	ecx			; Convert track to head & cyl
    95                              <1> 	; eax (ax) = cylinder, dx (dl) = head (max. FFh)
    96 0000FDEF 88D6                <1> 	mov	dh, dl
    97 0000FDF1 6659                <1> 	pop	cx			; AX=Cyl, DH=Head, CX=Sector
    98 0000FDF3 8A5602              <1> 	mov	dl, [esi+LD_PhyDrvNo]
    99                              <1> 
   100 0000FDF6 88C5                <1> 	mov	ch, al			; NOTE: max. 1023 cylinders !                   
   101 0000FDF8 C0CC02              <1> 	ror	ah, 2			; Rotate 2 bits right
   102 0000FDFB 08E1                <1> 	or	cl, ah
   103                              <1> 
   104                              <1> 	; 24/02/2016
   105                              <1> 	;pop	eax ; * (spt - sec) (example: 63 - 0 = 63)
   106                              <1> 	;cmp	eax, [sector_count]
   107                              <1> 	;jb	short chs_write_sectors
   108                              <1> 	;je	short chs_read_sectors
   109                              <1> 	;; (# of sectors to read is more than remaining sectors on the track)
   110                              <1> 	;mov	al, [sector_count]
   111                              <1> ;chs_read_sectors: ; read or write !
   112 0000FDFD B001                <1> 	mov	al, 1 ; 25/02/2016
   113 0000FDFF 8A25[35670100]      <1> 	mov	ah, [disk_rw_op]  ; 02h = chs read, 03h = chs write 
   114                              <1> 	;
   115 0000FE05 E8314BFFFF          <1> 	call	int13h			; BIOS Service func ( ah ) = 2
   116                              <1>                                         ; Read disk sectors
   117                              <1>                                         ; AL-sec num CH-track CL-sec
   118                              <1>                                         ; DH-head DL-drive ES:BX-buffer
   119                              <1>                                         ; CF-flag AH-stat AL-sec read
   120                              <1> 	                                ; If CF = 1 then (If AH > 0)
   121 0000FE0A 8825[37670100]      <1> 	mov	[disk_rw_err], ah
   122                              <1> 	
   123 0000FE10 59                  <1> 	pop	ecx
   124 0000FE11 58                  <1> 	pop	eax
   125 0000FE12 7314                <1> 	jnc	short chs_read_ok
   126                              <1> 
   127 0000FE14 803D[37670100]09    <1> 	cmp	byte [disk_rw_err], 09h ; DMA crossed 64K segment boundary
   128 0000FE1B 7408                <1> 	je	short chs_read_error_retn
   129                              <1>              
   130 0000FE1D FE0D[36670100]      <1> 	dec	byte [retry_count]
   131 0000FE23 75B0                <1> 	jnz	short chs_read_retry
   132                              <1> 
   133                              <1> chs_read_error_retn:
   134 0000FE25 F9                  <1> 	stc
   135                              <1> 	;retn
   136 0000FE26 EB69                <1> 	jmp	short update_drv_error_byte
   137                              <1> 
   138                              <1> ;chs_write_sectors: ; read or write 
   139                              <1> 	;; (# of sectors to read is less than remaining sectors on the track)
   140                              <1> 	;mov	[sector_count], al
   141                              <1> 	;jmp	short chs_read_sectors
   142                              <1> 
   143                              <1> chs_read_ok:
   144                              <1> 	;; 23/02/2016
   145                              <1> 	;movzx	edx, byte [sector_count] ; sector count (<= spt)	
   146                              <1>         ;sub    ecx, edx  ; remaining sector count
   147                              <1> 	;jna	short update_drv_error_byte	
   148                              <1> 	;add	eax, edx ; next disk sector
   149                              <1> 	;shl	edx, 9 ; 512 * sector count
   150                              <1> 	;add	ebx, edx ; next buffer byte address 
   151                              <1>         ;jmp     chs_read_next_sector        
   152                              <1> 	; 25/02/2016
   153 0000FE28 40                  <1> 	inc	eax ; next sector
   154 0000FE29 81C300020000        <1> 	add	ebx, 512
   155 0000FE2F E29D                <1> 	loop	chs_read_next_sector
   156 0000FE31 EB5E                <1> 	jmp	short update_drv_error_byte
   157                              <1> 
   158                              <1> lba_write:
   159                              <1> 	; 23/02/2016
   160 0000FE33 C605[35670100]1C    <1> 	mov	byte [disk_rw_op], 1Ch ; LBA write
   161 0000FE3A EB07                <1> 	jmp	short lba_rw
   162                              <1> 
   163                              <1> lba_read:
   164                              <1> 	; 23/02/2016
   165                              <1> 	; 17/02/2016
   166                              <1> 	; 14/02/2016
   167                              <1> 	; 13/02/2016
   168                              <1> 	; 31/01/2016 (TRDOS 386 =  TRDOS v2.0)
   169                              <1> 	; 10/07/2015 (Retro UNIX 386 v1)
   170                              <1> 	;
   171                              <1> 	; INPUT -> EAX = Logical Block Address
   172                              <1> 	;	   ESI = Logical Dos Disk Table Offset (DRV)	
   173                              <1> 	;	   ECX = Sector Count	
   174                              <1> 	; 	   EBX = Destination Buffer
   175                              <1> 	; OUTPUT -> 
   176                              <1> 	;	   cf = 0 or cf = 1
   177                              <1> 	; (Modified registers: EAX, EBX, ECX, EDX)
   178                              <1> 
   179                              <1> 	; LBA read/write (with private LBA function) 
   180                              <1> 	;((Retro UNIX 386 v1 - DISK I/O code by Erdogan Tan))
   181                              <1> 
   182                              <1> 
   183                              <1> 	; 23/02/2016
   184 0000FE3C C605[35670100]1B    <1> 	mov	byte [disk_rw_op], 1Bh ; LBA read
   185                              <1> 
   186                              <1> lba_rw:
   187                              <1> 	; 17/02/2016
   188 0000FE43 57                  <1> 	push	edi
   189                              <1> 
   190 0000FE44 890D[38670100]      <1> 	mov	[sector_count], ecx ; total sector (read) count
   191                              <1> 
   192 0000FE4A 8A5602              <1> 	mov	dl, [esi+LD_PhyDrvNo]
   193                              <1> 	; dl = physical drive number (0,1, 80h, 81h, 82h, 83h)
   194                              <1> 
   195                              <1> lba_read_next:
   196 0000FE4D 81F900010000        <1> 	cmp	ecx, 256
   197 0000FE53 7605                <1> 	jna	short lba_read_rsc
   198 0000FE55 B900010000          <1> 	mov	ecx, 256 ; 17/02/2016
   199                              <1> lba_read_rsc:
   200 0000FE5A 290D[38670100]      <1> 	sub	[sector_count], ecx ; remain sectors
   201                              <1> 
   202 0000FE60 89CF                <1> 	mov	edi, ecx 
   203 0000FE62 89C1                <1> 	mov	ecx, eax ; sector number/address
   204                              <1> 
   205 0000FE64 C605[36670100]04    <1> 	mov	byte [retry_count], 4
   206                              <1> lba_read_retry:
   207 0000FE6B 89F8                <1> 	mov	eax, edi
   208                              <1> 	;
   209                              <1> 	; ecx = sector number
   210                              <1> 	; al = sector count (0 - 255) /// (0 = 256)
   211                              <1> 	; dl = drive number
   212                              <1> 	; ebx = buffer offset
   213                              <1> 	;
   214                              <1> 	; Function 1Bh = LBA read, 1Ch = LBA write
   215                              <1> 	; 23/02/2016
   216 0000FE6D 8A25[35670100]      <1> 	mov	ah, [disk_rw_op] ; 1Bh = LBA read, 1Ch = LBA write
   217 0000FE73 E8C34AFFFF          <1> 	call	int13h
   218                              <1> 	; al = ? (changed)
   219                              <1> 	; ah = error code
   220 0000FE78 8825[37670100]      <1> 	mov	[disk_rw_err], ah
   221 0000FE7E 7334                <1> 	jnc	short lba_read_ok
   222 0000FE80 80FC80              <1> 	cmp	ah, 80h ; time out?
   223 0000FE83 740A                <1>         je      short lba_read_stc_retn
   224 0000FE85 FE0D[36670100]      <1> 	dec	byte [retry_count]
   225 0000FE8B 7FDE                <1> 	jg	short lba_read_retry
   226 0000FE8D 743A                <1> 	jz	short lba_read_reset
   227                              <1> 	; sf =  1
   228                              <1> 
   229                              <1> lba_read_stc_retn:
   230 0000FE8F F9                  <1> 	stc
   231                              <1> lba_read_retn:
   232 0000FE90 5F                  <1> 	pop	edi
   233                              <1> 
   234                              <1> update_drv_error_byte:
   235 0000FE91 9C                  <1> 	pushf
   236 0000FE92 53                  <1> 	push	ebx
   237 0000FE93 6651                <1> 	push	cx
   238                              <1> 	;or	ecx, ecx
   239                              <1> 	;jz	short udrv_errb0
   240 0000FE95 8A0D[37670100]      <1> 	mov	cl, [disk_rw_err]
   241                              <1> udrv_errb0:
   242 0000FE9B 0FB65E02            <1> 	movzx	ebx, byte [esi+LD_PhyDrvNo]
   243 0000FE9F 80FB02              <1> 	cmp	bl, 2
   244 0000FEA2 7203                <1>         jb      short udrv_errb1
   245 0000FEA4 80EB7E              <1> 	sub	bl, 7Eh
   246                              <1> 	;cmp	bl, 5
   247                              <1> 	;ja	short udrv_errb2	
   248                              <1> udrv_errb1:
   249 0000FEA7 81C3[01650000]      <1>         add     ebx, drv.error ; 13/02/2016
   250 0000FEAD 880B                <1> 	mov	[ebx], cl ; error code
   251                              <1> udrv_errb2:
   252 0000FEAF 6659                <1> 	pop	cx
   253 0000FEB1 5B                  <1> 	pop	ebx
   254 0000FEB2 9D                  <1> 	popf
   255 0000FEB3 C3                  <1> 	retn
   256                              <1> 
   257                              <1> lba_read_ok:
   258 0000FEB4 89C8                <1> 	mov	eax, ecx ; sector number
   259 0000FEB6 01F8                <1> 	add	eax, edi ; sector number (next)
   260 0000FEB8 C1E709              <1> 	shl	edi, 9 ; sector count * 512
   261 0000FEBB 01FB                <1> 	add	ebx, edi ; next buffer offset
   262                              <1> 
   263 0000FEBD 8B0D[38670100]      <1> 	mov	ecx, [sector_count] ; remaining sectors
   264 0000FEC3 09C9                <1> 	or	ecx, ecx
   265 0000FEC5 7586                <1> 	jnz	short lba_read_next
   266 0000FEC7 EBC7                <1> 	jmp	short lba_read_retn
   267                              <1> 
   268                              <1> lba_read_reset:
   269 0000FEC9 B40D                <1> 	mov	ah, 0Dh ; Alternate reset
   270 0000FECB E86B4AFFFF          <1>         call	int13h
   271                              <1> 	; al = ? (changed)
   272                              <1> 	; ah = error code
   273 0000FED0 7399                <1> 	jnc	short lba_read_retry
   274 0000FED2 EBBC                <1> 	jmp	short lba_read_retn
  2868                                  %include 'trdosk8.s' ; 24/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.2) - MAIN PROGRAM : trdosk8.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 03/08/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    11                              <1> ; u0.s (20/11/2015), u4.s (14/10/2015)
    12                              <1> ; ****************************************************************************
    13                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    14                              <1> ; TRDOS2.ASM (09/11/2011)
    15                              <1> ; ----------------------------------------------------------------------------
    16                              <1> ; DIR.ASM (c) 2004-2011 Erdogan TAN  [07/01/2004] Last Update: 09/10/2011
    17                              <1> 
    18                              <1> set_run_sequence:
    19                              <1> 	; 23/12/2016
    20                              <1> 	; 10/06/2016
    21                              <1> 	; 22/05/2016
    22                              <1> 	; 20/05/2016
    23                              <1> 	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
    24                              <1> 	; TRDOS 386 feature only !
    25                              <1> 	;
    26                              <1> 	; INPUT ->
    27                              <1> 	;	AL = process number (next process)
    28                              <1> 	;
    29                              <1> 	;	this process must be added to run sequence
    30                              <1> 	;
    31                              <1> 	;	[u.pri] = priority of present process
    32                              <1> 	;
    33                              <1> 	;	DL = priority (queue)
    34                              <1> 	;	     0 = background (low) ; run on background 
    35                              <1> 	;	     1 = regular (normal) ; run as regular
    36                              <1> 	;	     2 = event (high)     ; run for event
    37                              <1> 	;
    38                              <1> 	;	1) If the requested process is already running:
    39                              <1> 	;	   a) If present priority is high ([u.pri]=2) 
    40                              <1> 	;	      and requested priority is also high, 
    41                              <1> 	;	      there is nothing to do! Because it has been
    42                              <1> 	;	      done already (before this attempt).		 	
    43                              <1> 	;	   b) If present priority is high ([u.pri]=2)
    44                              <1> 	;	      and requested priority is not high, there is
    45                              <1> 	;	      nothing to do! Because, it's current
    46                              <1> 	;	      run queue is unspecified, here. (It may be in
    47                              <1> 	;	      a waiting list or in a run queue; if the new
    48                              <1> 	;	      priority would be used to add it to relavant
    49                              <1>         ;             run queue, this would be wrong, unnecessary
    50                              <1> 	;	      and destabilizing duplication!)
    51                              <1> 	;	   c) If present priority is not high ([u.pri]<2)
    52                              <1>         ;             and requested priority is high (event),
    53                              <1> 	;	      process will be added to present priority's
    54                              <1> 	;	      run queue and then, priority will be changed
    55                              <1> 	;	      to high ([u.pri]=2).
    56                              <1> 	;	   d) If present priority is not high ([u.pri]<2)
    57                              <1> 	;	      and requested priority is not high, [u.pri]
    58                              <1> 	;	      value will be changed. There is nothing to do
    59                              <1> 	;	      in addition. (The new priority value will be
    60                              <1> 	;	      used by 'tswap/tswitch' procedure at 'sysret'
    61                              <1> 	;	      or 'sysrele' stage.)
    62                              <1> 	;
    63                              <1> 	;	2) If the requested process is not running:
    64                              <1> 	;	   a) If requested priority of the requested
    65                              <1> 	;	      (next) process is high (event) and priority
    66                              <1> 	;	      of present process is not high, the requested
    67                              <1> 	;	      process will be added to ('runq_event') high
    68                              <1> 	;	      priority run queue and then present (running)
    69                              <1> 	;	      process will be stopped (swapped/switched out)
    70                              <1> 	;	      immediately if it is in user mode, or it's 
    71                              <1> 	;	      [u.quant] value will be reset to 0 and (then) 
    72                              <1> 	;	      it will be stopped at 'sysret' stage.			
    73                              <1> 	;	   b) If requested priority of the requested
    74                              <1> 	;	      (next) process is high (event) and priority
    75                              <1> 	;	      of present process is also high, the requested
    76                              <1> 	;	      process will be added to ('runq_event') high
    77                              <1> 	;	      priority run queue and present (running) 
    78                              <1> 	;	      process will be allowed to run until it's 
    79                              <1> 	;	      time quantum will be elapsed ([u.quant]=0).	
    80                              <1> 	;	   c) If requested priority of the requested
    81                              <1> 	;	      (next) process is not high ('run for event'), 
    82                              <1> 	;	      there is nothing to do. Because, it's current
    83                              <1> 	;	      run queue is unspecified, here. (It may be in
    84                              <1> 	;	      a waiting list or in a run queue; if the new
    85                              <1> 	;	      priority would be used to add it to relavant
    86                              <1>         ;             run queue, this would be wrong, unnecessary
    87                              <1> 	;	      and destabilizing duplication!) 
    88                              <1> 	;
    89                              <1> 	; OUTPUT ->
    90                              <1> 	;	none
    91                              <1> 	;
    92                              <1> 	;	[u.pri] = priority of present process
    93                              <1> 	;
    94                              <1> 	;	cf = 1, if the request could not be fulfilled.
    95                              <1> 	;			 	     	  
    96                              <1> 	;	NOTE: 
    97                              <1>         ;          * Processes in 'run as regular' queue can run
    98                              <1> 	;	     if there is no process in 'run for event' queue
    99                              <1> 	;	     ('run for event' processes have higher priority)	 		 
   100                              <1> 	;	   * When [u.quant] time quantum of a process is
   101                              <1> 	;	     elapsed, it's high priority ('run for event')
   102                              <1> 	;	     status will be disabled, it can be run in sequence
   103                              <1> 	;	     of it's actual run queue.
   104                              <1> 	;	   * A 'run on background' process will always be 
   105                              <1> 	;	     sequenced in 'run on background' (low priority)
   106                              <1> 	;	     queue, it can run only when other priority queues
   107                              <1> 	;	     are empty. (idle time processes, e.g. printing)  	 	
   108                              <1> 	;
   109                              <1> 	; Modified registers: eax, ebx, edx
   110                              <1> 	;
   111                              <1> 
   112                              <1> srunseq_0:
   113 0000FED4 3A05[B3030300]      <1>         cmp     al, [u.uno]     ; same process ?
   114 0000FEDA 750C                <1> 	jne	short srunseq_2 ; no
   115                              <1> 
   116 0000FEDC 8A25[A9030300]      <1> 	mov	ah, [u.pri] 	; present/current priority
   117 0000FEE2 80FC02              <1> 	cmp	ah, 2       	; 'run for event' priority level
   118 0000FEE5 7221                <1> 	jb	short srunseq_6 ; no
   119                              <1> 
   120                              <1> srunseq_1:
   121                              <1> 	; there is nothing to do!
   122 0000FEE7 C3                  <1> 	retn
   123                              <1> 
   124                              <1> srunseq_2:
   125                              <1> 	;;this not necessary ! 23/12/2016
   126                              <1>         ;;cmp	al, nproc	; number of processes = 16 
   127                              <1> 	;;jnb	short srunseq_5	; error ! invalid process number 
   128                              <1> 
   129                              <1> 	; dl = priority
   130 0000FEE8 80FA02              <1> 	cmp	dl, 2 		; event queue
   131 0000FEEB 72FA                <1> 	jb	short srunseq_1 ; requested process is not present
   132                              <1> 				; process and priority of requested
   133                              <1> 				; process is not high (event), 
   134                              <1> 				; there is nothing to do!
   135                              <1> 	
   136                              <1> 	; requested process is not present process
   137                              <1> 	; & priority of requested process is high
   138 0000FEED 3A15[A9030300]      <1> 	cmp	dl, [u.pri] 	; priority of present process
   139 0000FEF3 7606                <1> 	jna	short srunseq_3 ; is high, also
   140                              <1> 	;
   141                              <1> 	; present process will be swapped/switched out
   142 0000FEF5 FE05[116B0100]      <1> 	inc	byte [p_change] ; 1
   143                              <1> 
   144                              <1> srunseq_3:
   145                              <1> 	; add process to 'runq_event' queue for new event
   146 0000FEFB BB[52030300]        <1> 	mov	ebx, runq_event ; high priority run queue
   147                              <1> 
   148                              <1> srunseq_4:
   149                              <1> 	; al = process number
   150                              <1> 	; ebx = run queue
   151 0000FF00 E881EDFFFF          <1> 	call	putlu
   152 0000FF05 C3                  <1> 	retn
   153                              <1> 
   154                              <1> srunseq_5:
   155 0000FF06 F5                  <1> 	cmc
   156 0000FF07 C3                  <1> 	retn
   157                              <1> 
   158                              <1> srunseq_6:
   159                              <1> 	; present priority of the process is not high
   160                              <1> 	
   161 0000FF08 8815[A9030300]      <1> 	mov	[u.pri], dl ; new priority 
   162                              <1> 			    ; (will be used by 'tswap')
   163                              <1> 
   164 0000FF0E 80FA02              <1> 	cmp	dl, 2 		; high priority ?
   165 0000FF11 72F3                <1> 	jb	short srunseq_5 ; no, there is nothing to do
   166                              <1> 				; in addition
   167                              <1> 
   168                              <1> 	; process must be added to relevant run queue, here!
   169                              <1> 	; (new priority is high/event priority and process
   170                              <1> 	; will not be added to a run queue by 'tswap')
   171                              <1> 
   172 0000FF13 BB[54030300]        <1> 	mov	ebx, runq_normal ; 'run as regular' queue
   173                              <1> 
   174 0000FF18 20E4                <1> 	and	ah, ah  ;  previous value of [u.pri]
   175 0000FF1A 75E4                <1> 	jnz	short srunseq_4
   176                              <1> 
   177 0000FF1C 43                  <1> 	inc	ebx
   178 0000FF1D 43                  <1> 	inc	ebx
   179                              <1> 	; ebx = runq_background ; 'run on backgroud' queue 
   180                              <1> 
   181 0000FF1E EBE0                <1> 	jmp	short srunseq_4
   182                              <1> clock:
   183                              <1> 	; 23/05/2016
   184                              <1> 	; 22/05/2016
   185                              <1> 	; 20/05/2016
   186                              <1> 	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
   187                              <1> 	; 14/05/2015 - 14/10/2015 (Retro UNIX 386 v1)
   188                              <1> 	; 07/12/2013 - 10/04/2014 (Retro UNIX 8086 v1)
   189                              <1> 
   190 0000FF20 803D[A8030300]00    <1> 	cmp	byte [u.quant], 0
   191 0000FF27 772C                <1> 	ja	short clk_1
   192                              <1> 	;
   193 0000FF29 803D[B3030300]01    <1> 	cmp     byte [u.uno], 1 ; /etc/init ? (for Retro UNIX 8086 & 386 v1)
   194                              <1> 				; MainProg (Kernel's Command Interpreter)
   195                              <1> 				; for TRDOS 386.
   196 0000FF30 7623                <1> 	jna	short clk_1 ; yes, do not swap out
   197                              <1> 	;
   198 0000FF32 803D[5B030300]FF    <1> 	cmp     byte [sysflg], 0FFh ; user or system space ?
   199 0000FF39 7520                <1> 	jne	short clk_2 	    ; system space (sysflg <> 0FFh)
   200                              <1> 	;
   201 0000FF3B 66833D[AA030300]00  <1> 	cmp	word [u.intr], 0
   202 0000FF43 7616                <1> 	jna	short clk_2
   203                              <1> 	;
   204                              <1> 	; 23/05/2016
   205 0000FF45 803D[126B0100]00    <1> 	cmp	byte [multi_tasking], 0
   206 0000FF4C 760D                <1> 	jna	short clk_2
   207                              <1> 	;
   208 0000FF4E FE05[116B0100]      <1> 	inc	byte [p_change] ; it is time to change running process	
   209 0000FF54 C3                  <1> 	retn
   210                              <1> clk_1:
   211 0000FF55 FE0D[A8030300]      <1> 	dec	byte [u.quant]
   212                              <1> clk_2:
   213 0000FF5B C3                  <1> 	retn   ; return to (hardware) timer interrupt routine
   214                              <1> 
   215                              <1> ; 12/10/2017
   216                              <1> ; 15/01/2017
   217                              <1> ; 14/01/2017
   218                              <1> ; 07/01/2017
   219                              <1> ; 02/01/2017
   220                              <1> ; 17/08/2016
   221                              <1> ; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   222                              <1> int34h:  ; #IOCTL# (I/O port access support for ring 3)
   223                              <1> ; 23/05/2016
   224                              <1> 	; 20/06/2016
   225                              <1> 	; 29/04/2016 - TRDOS 386 (TRDOS v2.0)
   226                              <1> 	;
   227                              <1> 	; INPUT ->
   228                              <1> 	;	AH = 0 -> read port  (physical IO port) -byte-
   229                              <1> 	;	AH = 1 -> write port (physical IO port) -byte-
   230                              <1> 	;		AL = data byte
   231                              <1> 	;	AH = 2 -> read port  (physical IO port) -word-
   232                              <1> 	;	AH = 3 -> write port (physical IO port) -word-
   233                              <1> 	;		BX = data word
   234                              <1> 	;	AH = 4 -> read port  (physical IO port) -dword-
   235                              <1> 	;	AH = 5 -> write port (physical IO port) -dword-
   236                              <1> 	;		EBX = data dword
   237                              <1> 	;	; 12/10/2017
   238                              <1> 	;	AH = 6 -> read port (physical IO port) twice -byte-
   239                              <1> 	;	AH = 7 -> write port (physical IO port) twice -byte-
   240                              <1> 	;		BX = data word	
   241                              <1> 	;
   242                              <1> 	;	DX = Port number (<= 0FFFFh)
   243                              <1> 	;
   244                              <1> 	; OUTPUT ->
   245                              <1> 	;	AL = data byte (in al, dx)
   246                              <1> 	;	AX = data word (in ax, dx)
   247                              <1> 	;	EAX = data dword (in eax, dx)
   248                              <1> 	;
   249                              <1> 	;	(ECX = actual TRANSFER COUNT for string functions)
   250                              <1> 	;
   251                              <1> 	;
   252                              <1> 	; Modified registers: EAX
   253                              <1> 	;
   254                              <1> 
   255                              <1> 	;cmp	ah, 5
   256                              <1> 	;ja	short int34h_5 ; invalid function !
   257                              <1> 
   258                              <1> 	; 12/10/2017
   259 0000FF5C 80FC07              <1> 	cmp	ah, 7
   260 0000FF5F 7743                <1> 	ja	short int34h_5 ; invalid function !
   261                              <1> 
   262                              <1> 	;; 15/01/2017
   263                              <1> 	; 14/01/2017
   264                              <1> 	; 02/01/2017
   265                              <1> 	;;mov	byte [ss:intflg], 34h	; IOCTL interrupt 
   266 0000FF61 FB                  <1> 	sti
   267                              <1> 	
   268                              <1> 	;sti	; enable interrupts
   269 0000FF62 80642408FE          <1> 	and	byte [esp+8], 11111110b	; clear carry bit of eflags register
   270                              <1> 
   271 0000FF67 80FC01              <1> 	cmp	ah, 1
   272 0000FF6A 7205                <1> 	jb	short int34h_0
   273 0000FF6C 7705                <1> 	ja	short int34h_1
   274                              <1> 
   275 0000FF6E EE                  <1> 	out	dx, al
   276                              <1> 	;iretd
   277 0000FF6F EB01                <1> 	jmp short int34h_iret
   278                              <1> 
   279                              <1> int34h_0:
   280 0000FF71 EC                  <1> 	in	al, dx
   281                              <1> 	;iretd
   282                              <1> int34h_iret:
   283                              <1> 	;cli	; 07/01/2017
   284                              <1> 	;; 15/01/2017
   285                              <1> 	;;mov	byte [ss:intflg], 0 ; reset
   286 0000FF72 CF                  <1> 	iretd 
   287                              <1> 
   288                              <1> int34h_1:
   289 0000FF73 F6C401              <1> 	test	ah, 1
   290 0000FF76 7516                <1> 	jnz	short int34h_3 ; out
   291                              <1> 
   292                              <1> 	; in
   293 0000FF78 80FC02              <1> 	cmp	ah, 2
   294 0000FF7B 7707                <1> 	ja	short int34h_2
   295                              <1> 
   296 0000FF7D 6689D8              <1> 	mov	ax, bx
   297 0000FF80 66ED                <1> 	in	ax, dx
   298                              <1> 	;iretd
   299 0000FF82 EBEE                <1> 	jmp	short int34h_iret
   300                              <1> 
   301                              <1> int34h_2:
   302 0000FF84 80FC04              <1> 	cmp	ah, 4
   303 0000FF87 772C                <1> 	ja	short int34h_7	; 12/10/2017
   304                              <1> 	; ah = 4
   305 0000FF89 89D8                <1> 	mov	eax, ebx
   306 0000FF8B ED                  <1> 	in	eax, dx
   307                              <1> 	;iretd
   308 0000FF8C EBE4                <1> 	jmp	short int34h_iret
   309                              <1> 
   310                              <1> int34h_3:
   311 0000FF8E 80FC03              <1> 	cmp	ah, 3
   312 0000FF91 7707                <1> 	ja	short int34h_4
   313                              <1> 
   314 0000FF93 6689D8              <1> 	mov	ax, bx
   315 0000FF96 66EF                <1> 	out	dx, ax
   316                              <1> 	;iretd
   317 0000FF98 EBD8                <1> 	jmp	short int34h_iret
   318                              <1> 
   319                              <1> int34h_4:
   320 0000FF9A 80FC05              <1> 	cmp	ah, 5
   321 0000FF9D 770B                <1> 	ja	short int34h_6	; 12/10/2017
   322                              <1> 	; ah = 5
   323 0000FF9F 89D8                <1> 	mov	eax, ebx
   324 0000FFA1 EF                  <1> 	out	dx, eax
   325                              <1> 	;iretd
   326 0000FFA2 EBCE                <1> 	jmp	short int34h_iret
   327                              <1> 
   328                              <1> int34h_5:
   329 0000FFA4 804C240801          <1> 	or	byte [esp+8], 1	; set carry bit of eflags register
   330 0000FFA9 CF                  <1> 	iretd
   331                              <1> 
   332                              <1> 	; 12/10/2017
   333                              <1> int34h_6:
   334 0000FFAA 6689D8              <1> 	mov	ax, bx
   335 0000FFAD EE                  <1> 	out	dx, al
   336 0000FFAE EB00                <1> 	jmp	short $+2
   337 0000FFB0 86E0                <1> 	xchg	ah, al
   338 0000FFB2 EE                  <1> 	out	dx, al
   339                              <1> 	;xchg	al, ah
   340                              <1> 	;iretd
   341 0000FFB3 EB06                <1> 	jmp	short int34h_8
   342                              <1> int34h_7:
   343 0000FFB5 EC                  <1> 	in	al, dx
   344 0000FFB6 EB00                <1> 	jmp	short $+2
   345 0000FFB8 88C4                <1> 	mov	ah, al
   346 0000FFBA EC                  <1> 	in	al, dx
   347                              <1> int34h_8:
   348 0000FFBB 86C4                <1> 	xchg	al, ah
   349 0000FFBD CF                  <1> 	iretd
   350                              <1> 			
   351                              <1> 
   352                              <1> INT4Ah:
   353                              <1> 	; 24/01/2016
   354                              <1> 	; this procedure will be called by 'RTC_INT' (in 'timer.s')
   355 0000FFBE C3                  <1> 	retn
   356                              <1> 
   357                              <1> ; u0.s
   358                              <1> ; Retro UNIX 386 v1 Kernel (v0.2) - SYS0.INC
   359                              <1> ; Last Modification: 20/11/2015
   360                              <1> 
   361                              <1> com2_int:
   362                              <1> 	; 07/11/2015 
   363                              <1> 	; 24/10/2015
   364                              <1> 	; 23/10/2015
   365                              <1> 	; 14/03/2015 (Retro UNIX 386 v1 - Beginning)
   366                              <1> 	; 28/07/2014 (Retro UNIX 8086 v1)
   367                              <1> 	; < serial port 2 interrupt handler >
   368                              <1> 	;
   369 0000FFBF 890424              <1> 	mov 	[esp], eax ; overwrite call return address
   370                              <1> 	;push	eax
   371 0000FFC2 66B80900            <1> 	mov	ax, 9
   372 0000FFC6 EB07                <1> 	jmp	short comm_int
   373                              <1> com1_int:
   374                              <1> 	; 07/11/2015
   375                              <1> 	; 24/10/2015
   376 0000FFC8 890424              <1> 	mov 	[esp], eax ; overwrite call return address
   377                              <1> 	; 23/10/2015
   378                              <1> 	;push	eax
   379 0000FFCB 66B80800            <1> 	mov	ax, 8
   380                              <1> comm_int:
   381                              <1> 	; 20/11/2015
   382                              <1> 	; 18/11/2015
   383                              <1> 	; 17/11/2015
   384                              <1> 	; 16/11/2015
   385                              <1> 	; 09/11/2015
   386                              <1> 	; 08/11/2015
   387                              <1> 	; 07/11/2015
   388                              <1> 	; 06/11/2015 (serial4.asm, 'serial')	
   389                              <1> 	; 01/11/2015
   390                              <1> 	; 26/10/2015
   391                              <1> 	; 23/10/2015
   392 0000FFCF 53                  <1> 	push	ebx
   393 0000FFD0 56                  <1> 	push	esi
   394 0000FFD1 57                  <1> 	push	edi
   395 0000FFD2 1E                  <1> 	push 	ds
   396 0000FFD3 06                  <1> 	push 	es
   397                              <1> 	; 18/11/2015
   398 0000FFD4 0F20DB              <1> 	mov	ebx, cr3
   399 0000FFD7 53                  <1> 	push	ebx ; ****
   400                              <1> 	;
   401 0000FFD8 51                  <1> 	push	ecx ; ***
   402 0000FFD9 52                  <1> 	push	edx ; **
   403                              <1> 	;
   404 0000FFDA BB10000000          <1> 	mov	ebx, KDATA
   405 0000FFDF 8EDB                <1> 	mov	ds, bx
   406 0000FFE1 8EC3                <1> 	mov	es, bx
   407                              <1> 	;
   408 0000FFE3 8B0D[805E0100]      <1> 	mov	ecx, [k_page_dir]
   409 0000FFE9 0F22D9              <1> 	mov	cr3, ecx
   410                              <1> 	; 20/11/2015
   411                              <1> 	; Interrupt identification register
   412 0000FFEC 66BAFA02            <1> 	mov	dx, 2FAh ; COM2
   413                              <1> 	;
   414 0000FFF0 3C08                <1> 	cmp 	al, 8 
   415 0000FFF2 7702                <1> 	ja 	short com_i0
   416                              <1> 	;
   417                              <1> 	; 20/11/2015
   418                              <1> 	; 17/11/2015
   419                              <1> 	; 16/11/2015
   420                              <1> 	; 15/11/2015
   421                              <1> 	; 24/10/2015
   422                              <1> 	; 14/03/2015 (Retro UNIX 386 v1 - Beginning)
   423                              <1> 	; 28/07/2014 (Retro UNIX 8086 v1)
   424                              <1> 	; < serial port 1 interrupt handler >
   425                              <1> 	;
   426 0000FFF4 FEC6                <1> 	inc	dh ; 3FAh ; COM1 Interrupt id. register
   427                              <1> com_i0:
   428                              <1> 	;push	eax ; *
   429                              <1> 	; 07/11/2015
   430 0000FFF6 A2[EA5E0100]        <1> 	mov 	byte [ccomport], al
   431                              <1> 	; 09/11/2015
   432 0000FFFB 0FB7D8              <1> 	movzx	ebx, ax ; 8 or 9
   433                              <1> 	; 17/11/2015
   434                              <1>  	; reset request for response status
   435 0000FFFE 88A3[E05E0100]      <1> 	mov	[ebx+req_resp-8], ah ; 0
   436                              <1> 	;
   437                              <1> 	; 20/11/2015
   438 00010004 EC                  <1> 	in	al, dx		; read interrupt id. register
   439 00010005 EB00                <1> 	JMP	$+2	   	; I/O DELAY
   440 00010007 2404                <1> 	and	al, 4		; received data available?	
   441 00010009 7470                <1> 	jz	short com_eoi	; (transmit. holding reg. empty)
   442                              <1> 	;
   443                              <1> 	; 20/11/2015
   444 0001000B 80EA02              <1> 	sub	dl, 3FAh-3F8h	; data register (3F8h, 2F8h)
   445 0001000E EC                  <1> 	in	al, dx     	; read character
   446                              <1> 	;JMP	$+2	   	; I/O DELAY
   447                              <1> 	; 08/11/2015
   448                              <1> 	; 07/11/2015
   449 0001000F 89DE                <1> 	mov	esi, ebx 
   450 00010011 89DF                <1> 	mov	edi, ebx
   451 00010013 81C6[E45E0100]      <1> 	add 	esi, rchar - 8 ; points to last received char
   452 00010019 81C7[E65E0100]      <1> 	add	edi, schar - 8 ; points to last sent char
   453 0001001F 8806                <1> 	mov	[esi], al ; received char (current char)
   454                              <1> 	; query
   455 00010021 20C0                <1> 	and	al, al
   456 00010023 7527                <1> 	jnz	short com_i2
   457                              <1>    	; response
   458                              <1> 	; 17/11/2015
   459                              <1> 	; set request for response status
   460 00010025 FE83[E05E0100]      <1>         inc     byte [ebx+req_resp-8] ; 1 
   461                              <1> 	;
   462 0001002B 6683C205            <1> 	add	dx, 3FDh-3F8h	; (3FDh, 2FDh)
   463 0001002F EC                  <1> 	in	al, dx	   	; read line status register 
   464 00010030 EB00                <1> 	JMP	$+2	   	; I/O DELAY
   465 00010032 2420                <1> 	and	al, 20h	   	; transmitter holding reg. empty?
   466 00010034 7445                <1> 	jz	short com_eoi 	; no
   467 00010036 B0FF                <1> 	mov 	al, 0FFh   	; response			
   468 00010038 6683EA05            <1> 	sub	dx, 3FDh-3F8h 	; data port (3F8h, 2F8h)
   469 0001003C EE                  <1> 	out	dx, al	   	; send on serial port
   470                              <1> 	; 17/11/2015
   471 0001003D 803F00              <1> 	cmp 	byte [edi], 0   ; query ? (schar)
   472 00010040 7502                <1> 	jne 	short com_i1    ; no
   473 00010042 8807                <1> 	mov	[edi], al 	; 0FFh (responded)
   474                              <1> com_i1:
   475                              <1> 	; 17/11/2015
   476                              <1> 	; reset request for response status (again)
   477 00010044 FE8B[E05E0100]      <1>         dec     byte [ebx+req_resp-8] ; 0 
   478 0001004A EB2F                <1> 	jmp	short com_eoi
   479                              <1> com_i2:	
   480                              <1> 	; 08/11/2015
   481 0001004C 3CFF                <1> 	cmp 	al, 0FFh	; (response ?)
   482 0001004E 7417                <1> 	je	short com_i3	; (check for response signal)
   483                              <1> 	; 07/11/2015
   484 00010050 3C04                <1> 	cmp	al, 04h	; EOT
   485 00010052 751C                <1> 	jne	short com_i4	
   486                              <1> 	; EOT = 04h (End of Transmit) - 'CTRL + D'
   487                              <1> 	;(an EOT char is supposed as a ctrl+brk from the terminal)
   488                              <1> 	; 08/11/2015
   489                              <1> 		; ptty -> tty 0 to 7 (pseudo screens)
   490 00010054 861D[AE5E0100]      <1> 	xchg	bl, [ptty]  ; tty number (8 or 9)
   491 0001005A E81F6CFFFF          <1> 	call 	ctrlbrk
   492 0001005F 861D[AE5E0100]      <1> 	xchg	[ptty], bl ; (restore ptty value and BL value)
   493                              <1> 	;mov	al, 04h ; EOT
   494                              <1> 	; 08/11/2015
   495 00010065 EB09                <1> 	jmp	short com_i4	
   496                              <1> com_i3:
   497                              <1> 	; 08/11/2015
   498                              <1> 	; If 0FFh has been received just after a query
   499                              <1> 	; (schar, ZERO), it is a response signal.
   500                              <1> 	; 17/11/2015
   501 00010067 803F00              <1>         cmp     byte [edi], 0 ; query ? (schar)
   502 0001006A 7704                <1> 	ja	short com_i4 ; no
   503                              <1> 	; reset query status (schar)
   504 0001006C 8807                <1> 	mov	[edi], al ; 0FFh
   505 0001006E FEC0                <1> 	inc	al ; 0
   506                              <1> com_i4:
   507                              <1> 	; 27/07/2014
   508                              <1> 	; 09/07/2014
   509 00010070 D0E3                <1> 	shl	bl, 1	
   510 00010072 81C3[B05E0100]      <1> 	add	ebx, ttychr
   511                              <1> 	; 23/07/2014 (always overwrite)
   512                              <1> 	;;cmp	word [ebx], 0
   513                              <1> 	;;ja	short com_eoi
   514                              <1> 	;
   515 00010078 668903              <1> 	mov	[ebx], ax   ; Save ascii code
   516                              <1> 			    ; scan code = 0
   517                              <1> com_eoi:
   518                              <1> 	;mov	al, 20h
   519                              <1> 	;out	20h, al	   ; end of interrupt
   520                              <1> 	;
   521                              <1> 	; 07/11/2015
   522                              <1>       	;pop	eax ; *
   523 0001007B A0[EA5E0100]        <1> 	mov	al, byte [ccomport] ; current COM port
   524                              <1> 	 ; al = tty number (8 or 9)
   525 00010080 E85E010000          <1>         call	wakeup
   526                              <1> com_iret:
   527                              <1> 	; 23/10/2015
   528 00010085 5A                  <1> 	pop	edx ; **
   529 00010086 59                  <1> 	pop	ecx ; ***
   530                              <1> 	; 18/11/2015
   531                              <1> 	;pop	eax ; ****
   532                              <1> 	;mov	cr3, eax
   533                              <1> 	;jmp	iiret
   534 00010087 E9980CFFFF          <1> 	jmp	iiretp
   535                              <1> 
   536                              <1> ;iiretp: ; 01/09/2015
   537                              <1> ;	; 28/08/2015
   538                              <1> ;	pop	eax ; (*) page directory
   539                              <1> ;	mov	cr3, eax
   540                              <1> ;iiret:
   541                              <1> ;	; 22/08/2014
   542                              <1> ;	mov	al, 20h ; END OF INTERRUPT COMMAND TO 8259
   543                              <1> ;	out	20h, al	; 8259 PORT
   544                              <1> ;	;
   545                              <1> ;	pop	es
   546                              <1> ;	pop	ds
   547                              <1> ;	pop	edi
   548                              <1> ;	pop	esi
   549                              <1> ;	pop	ebx ; 29/08/2014
   550                              <1> ;	pop 	eax
   551                              <1> ;	iretd
   552                              <1> 
   553                              <1> sp_init:
   554                              <1> 	; 07/11/2015
   555                              <1> 	; 29/10/2015
   556                              <1> 	; 26/10/2015
   557                              <1> 	; 23/10/2015
   558                              <1> 	; 29/06/2015
   559                              <1> 	; 14/03/2015 (Retro UNIX 386 v1 - 115200 baud)
   560                              <1> 	; 28/07/2014 (Retro UNIX 8086 v1 - 9600 baud)
   561                              <1> 	; Initialization of Serial Port Communication Parameters
   562                              <1> 	; (COM1 base port address = 3F8h, COM1 Interrupt = IRQ 4)
   563                              <1> 	; (COM2 base port address = 2F8h, COM1 Interrupt = IRQ 3)
   564                              <1> 	;
   565                              <1> 	; ((Modified registers: EAX, ECX, EDX, EBX))
   566                              <1> 	;
   567                              <1> 	; INPUT:  (29/06/2015)
   568                              <1> 	;	AL = 0 for COM1
   569                              <1> 	;	     1 for COM2
   570                              <1> 	;	AH = Communication parameters	
   571                              <1> 	;
   572                              <1> 	;  (*) Communication parameters (except BAUD RATE):
   573                              <1> 	;	Bit	4	3	2	1	0
   574                              <1> 	;		-PARITY--   STOP BIT  -WORD LENGTH-	 		 
   575                              <1> 	;  this one -->	00 = none    0 = 1 bit  11 = 8 bits
   576                              <1> 	;		01 = odd     1 = 2 bits	10 = 7 bits
   577                              <1> 	;		11 = even
   578                              <1> 	;  Baud rate setting bits: (29/06/2015)
   579                              <1> 	;		Retro UNIX 386 v1 feature only !
   580                              <1> 	;	Bit	7    6    5  | Baud rate
   581                              <1> 	;		------------------------
   582                              <1> 	;	value	0    0    0  | Default (Divisor = 1)
   583                              <1> 	;		0    0    1  | 9600 (12)
   584                              <1> 	;		0    1    0  | 19200 (6) 
   585                              <1> 	;		0    1	  1  | 38400 (3) 
   586                              <1> 	;		1    0	  0  | 14400 (8)
   587                              <1> 	;		1    0	  1  | 28800 (4)
   588                              <1> 	;		1    1    0  | 57600 (2)
   589                              <1> 	;		1    1    1  | 115200 (1) 	
   590                              <1> 	
   591                              <1> 	; References:	
   592                              <1> 	; (1) IBM PC-XT Model 286 BIOS Source Code
   593                              <1> 	;     RS232.ASM --- 10/06/1985 COMMUNICATIONS BIOS (RS232)
   594                              <1> 	; (2) Award BIOS 1999 - ATORGS.ASM
   595                              <1> 	; (3) http://wiki.osdev.org/Serial_Ports
   596                              <1> 	;
   597                              <1> 	; Set communication parameters for COM1 (= 03h)	
   598                              <1> 	;
   599 0001008C BB[E65E0100]        <1> 	mov	ebx, com1p		; COM1 parameters  
   600 00010091 66BAF803            <1> 	mov	dx, 3F8h		; COM1
   601                              <1> 	 ; 29/10/2015
   602 00010095 66B90103            <1> 	mov	cx, 301h  ; divisor = 1 (115200 baud)
   603 00010099 E86F000000          <1> 	call	sp_i3	; call A4	
   604 0001009E A880                <1> 	test	al, 80h
   605 000100A0 7410                <1> 	jz	short sp_i0 ; OK..
   606                              <1> 		; Error !
   607                              <1> 	;mov	dx, 3F8h
   608 000100A2 80EA05              <1> 	sub	dl, 5 ; 3FDh -> 3F8h
   609 000100A5 66B90E03            <1> 	mov	cx, 30Eh  ; divisor = 12 (9600 baud)
   610 000100A9 E85F000000          <1> 	call	sp_i3	; call A4	
   611 000100AE A880                <1> 	test	al, 80h
   612 000100B0 7508                <1> 	jnz	short sp_i1
   613                              <1> sp_i0:
   614                              <1>         ; (Note: Serial port interrupts will be disabled here...)	
   615                              <1>         ; (INT 14h initialization code disables interrupts.)
   616                              <1> 	;
   617 000100B2 C603E3              <1> 	mov	byte [ebx], 0E3h ; 11100011b
   618 000100B5 E8DC000000          <1> 	call	sp_i5 ; 29/06/2015
   619                              <1> sp_i1:
   620 000100BA 43                  <1> 	inc	ebx
   621 000100BB 66BAF802            <1> 	mov	dx, 2F8h		; COM2
   622                              <1> 	 ; 29/10/2015
   623 000100BF 66B90103            <1> 	mov	cx, 301h  ; divisor = 1 (115200 baud)
   624 000100C3 E845000000          <1> 	call	sp_i3	; call A4	
   625 000100C8 A880                <1> 	test	al, 80h
   626 000100CA 7410                <1> 	jz	short sp_i2 ; OK..
   627                              <1> 		; Error !
   628                              <1> 	;mov	dx, 2F8h
   629 000100CC 80EA05              <1> 	sub	dl, 5 ; 2FDh -> 2F8h
   630 000100CF 66B90E03            <1> 	mov	cx, 30Eh  ; divisor = 12 (9600 baud)
   631 000100D3 E835000000          <1> 	call	sp_i3	; call A4	
   632 000100D8 A880                <1> 	test	al, 80h
   633 000100DA 7530                <1> 	jnz	short sp_i7
   634                              <1> sp_i2:
   635 000100DC C603E3              <1> 	mov	byte [ebx], 0E3h ; 11100011b
   636                              <1> sp_i6:
   637                              <1> 	;; COM2 - enabling IRQ 3
   638                              <1> 	; 07/11/2015
   639                              <1> 	; 26/10/2015
   640 000100DF 9C                  <1> 	pushf
   641 000100E0 FA                  <1> 	cli
   642                              <1> 	;
   643 000100E1 66BAFC02            <1> 	mov	dx, 2FCh   		; modem control register
   644 000100E5 EC                  <1> 	in	al, dx 	   		; read register
   645 000100E6 EB00                <1> 	JMP	$+2	   		; I/O DELAY
   646 000100E8 0C08                <1> 	or	al, 8      		; enable bit 3 (OUT2)
   647 000100EA EE                  <1> 	out	dx, al     		; write back to register
   648 000100EB EB00                <1> 	JMP	$+2	   		; I/O DELAY
   649 000100ED 66BAF902            <1> 	mov	dx, 2F9h   		; interrupt enable register
   650 000100F1 EC                  <1> 	in	al, dx     		; read register
   651 000100F2 EB00                <1> 	JMP	$+2	   		; I/O DELAY
   652                              <1> 	;or	al, 1      		; receiver data interrupt enable and
   653 000100F4 0C03                <1> 	or	al, 3	   		; transmitter empty interrupt enable
   654 000100F6 EE                  <1> 	out	dx, al 	   		; write back to register
   655 000100F7 EB00                <1> 	JMP	$+2        		; I/O DELAY
   656 000100F9 E421                <1> 	in	al, 21h    		; read interrupt mask register
   657 000100FB EB00                <1> 	JMP	$+2	   		; I/O DELAY
   658 000100FD 24F7                <1> 	and	al, 0F7h   		; enable IRQ 3 (COM2)
   659 000100FF E621                <1> 	out	21h, al    		; write back to register
   660                              <1> 	;
   661                              <1> 	; 23/10/2015
   662 00010101 B8[BFFF0000]        <1> 	mov 	eax, com2_int
   663 00010106 A3[DE010100]        <1> 	mov	[com2_irq3], eax
   664                              <1> 	; 26/10/2015
   665 0001010B 9D                  <1> 	popf	
   666                              <1> sp_i7:
   667 0001010C C3                  <1> 	retn
   668                              <1> 
   669                              <1> sp_i3:
   670                              <1> ;A4:  	;-----	INITIALIZE THE COMMUNICATIONS PORT
   671                              <1> 	; 28/10/2015
   672 0001010D FEC2                <1> 	inc	dl	; 3F9h (2F9h)	; 3F9h, COM1 Interrupt enable register 
   673 0001010F B000                <1> 	mov	al, 0
   674 00010111 EE                  <1> 	out	dx, al			; disable serial port interrupt
   675 00010112 EB00                <1> 	JMP	$+2			; I/O DELAY
   676 00010114 80C202              <1> 	add	dl, 2 	; 3FBh (2FBh)	; COM1 Line control register (3FBh)
   677 00010117 B080                <1> 	mov	al, 80h			
   678 00010119 EE                  <1> 	out	dx, al			; SET DLAB=1 ; divisor latch access bit
   679                              <1> 	;-----	SET BAUD RATE DIVISOR
   680                              <1> 	; 26/10/2015
   681 0001011A 80EA03              <1> 	sub 	dl, 3   ; 3F8h (2F8h)	; register for least significant byte
   682                              <1> 					; of the divisor value
   683 0001011D 88C8                <1> 	mov	al, cl	; 1
   684 0001011F EE                  <1> 	out	dx, al			; 1 = 115200 baud (Retro UNIX 386 v1)
   685                              <1> 					; 2 = 57600 baud
   686                              <1> 					; 3 = 38400 baud
   687                              <1> 					; 6 = 19200 baud
   688                              <1> 					; 12 = 9600 baud (Retro UNIX 8086 v1)
   689 00010120 EB00                <1> 	JMP	$+2			; I/O DELAY
   690 00010122 28C0                <1> 	sub	al, al
   691 00010124 FEC2                <1> 	inc	dl      ; 3F9h (2F9h)	; register for most significant byte
   692                              <1> 					; of the divisor value
   693 00010126 EE                  <1> 	out	dx, al ; 0
   694 00010127 EB00                <1> 	JMP	$+2			; I/O DELAY
   695                              <1> 	;	
   696 00010129 88E8                <1> 	mov	al, ch ; 3		; 8 data bits, 1 stop bit, no parity
   697                              <1> 	;and	al, 1Fh ; Bits 0,1,2,3,4	
   698 0001012B 80C202              <1> 	add	dl, 2	; 3FBh (2FBh)	; Line control register
   699 0001012E EE                  <1> 	out	dx, al			
   700 0001012F EB00                <1> 	JMP	$+2			; I/O DELAY
   701                              <1> 	; 29/10/2015
   702 00010131 FECA                <1> 	dec 	dl 	; 3FAh (2FAh)	; FIFO Control register (16550/16750)
   703 00010133 30C0                <1> 	xor	al, al			; 0
   704 00010135 EE                  <1> 	out	dx, al			; Disable FIFOs (reset to 8250 mode)
   705 00010136 EB00                <1> 	JMP	$+2	
   706                              <1> sp_i4:
   707                              <1> ;A18:	;-----	COMM PORT STATUS ROUTINE
   708                              <1> 	; 29/06/2015 (line status after modem status)
   709 00010138 80C204              <1> 	add	dl, 4	; 3FEh (2FEh)	; Modem status register
   710                              <1> sp_i4s:
   711 0001013B EC                  <1> 	in	al, dx			; GET MODEM CONTROL STATUS
   712 0001013C EB00                <1> 	JMP	$+2			; I/O DELAY
   713 0001013E 88C4                <1> 	mov	ah, al			; PUT IN (AH) FOR RETURN
   714 00010140 FECA                <1> 	dec	dl	; 3FDh (2FDh)	; POINT TO LINE STATUS REGISTER
   715                              <1> 					; dx = 3FDh for COM1, 2FDh for COM2
   716 00010142 EC                  <1> 	in	al, dx			; GET LINE CONTROL STATUS
   717                              <1> 	; AL = Line status, AH = Modem status
   718 00010143 C3                  <1> 	retn
   719                              <1> 
   720                              <1> sp_status:
   721                              <1> 	; 29/06/2015
   722                              <1> 	; 27/06/2015 (Retro UNIX 386 v1)
   723                              <1> 	; Get serial port status
   724 00010144 66BAFE03            <1> 	mov	dx, 3FEh		; Modem status register (COM1)
   725 00010148 28C6                <1> 	sub	dh, al			; dh = 2 for COM2 (al = 1)
   726                              <1> 					; dx = 2FEh for COM2
   727 0001014A EBEF                <1> 	jmp	short sp_i4s
   728                              <1> 
   729                              <1> sp_setp: ; Set serial port communication parameters
   730                              <1> 	; 07/11/2015
   731                              <1> 	; 29/10/2015
   732                              <1> 	; 29/06/2015
   733                              <1> 	; Retro UNIX 386 v1 feature only !	
   734                              <1> 	;
   735                              <1> 	; INPUT:
   736                              <1> 	;	AL = 0 for COM1
   737                              <1> 	;	     1 for COM2
   738                              <1> 	;	AH = Communication parameters (*)
   739                              <1> 	; OUTPUT:
   740                              <1> 	;	CL = Line status
   741                              <1> 	;	CH = Modem status
   742                              <1> 	;   If cf = 1 -> Error code in [u.error]
   743                              <1> 	;		 'invalid parameter !' 
   744                              <1> 	;		 	 or
   745                              <1> 	;		 'device not ready !' error
   746                              <1> 	;	
   747                              <1> 	;  (*) Communication parameters (except BAUD RATE):
   748                              <1> 	;	Bit	4	3	2	1	0
   749                              <1> 	;		-PARITY--   STOP BIT  -WORD LENGTH-	 		 
   750                              <1> 	;  this one -->	00 = none    0 = 1 bit  11 = 8 bits
   751                              <1> 	;		01 = odd     1 = 2 bits	10 = 7 bits
   752                              <1> 	;		11 = even
   753                              <1> 	;  Baud rate setting bits: (29/06/2015)
   754                              <1> 	;		Retro UNIX 386 v1 feature only !
   755                              <1> 	;	Bit	7    6    5  | Baud rate
   756                              <1> 	;		------------------------
   757                              <1> 	;	value	0    0    0  | Default (Divisor = 1)
   758                              <1> 	;		0    0    1  | 9600 (12)
   759                              <1> 	;		0    1    0  | 19200 (6) 
   760                              <1> 	;		0    1	  1  | 38400 (3) 
   761                              <1> 	;		1    0	  0  | 14400 (8)
   762                              <1> 	;		1    0	  1  | 28800 (4)
   763                              <1> 	;		1    1    0  | 57600 (2)
   764                              <1> 	;		1    1    1  | 115200 (1) 
   765                              <1> 	;
   766                              <1> 	; (COM1 base port address = 3F8h, COM1 Interrupt = IRQ 4)
   767                              <1> 	; (COM2 base port address = 2F8h, COM1 Interrupt = IRQ 3)
   768                              <1> 	;
   769                              <1> 	; ((Modified registers: EAX, ECX, EDX, EBX))
   770                              <1> 	;
   771 0001014C 66BAF803            <1> 	mov	dx, 3F8h
   772 00010150 BB[E65E0100]        <1> 	mov	ebx, com1p ; COM1 control byte offset
   773 00010155 3C01                <1> 	cmp	al, 1
   774 00010157 776B                <1> 	ja 	short sp_invp_err
   775 00010159 7203                <1> 	jb	short sp_setp1 ;  COM1 (AL = 0)
   776 0001015B FECE                <1> 	dec	dh ; 2F8h
   777 0001015D 43                  <1> 	inc	ebx ; COM2 control byte offset
   778                              <1> sp_setp1:
   779                              <1> 	; 29/10/2015
   780 0001015E 8823                <1> 	mov	[ebx], ah
   781 00010160 0FB6CC              <1> 	movzx 	ecx, ah
   782 00010163 C0E905              <1> 	shr	cl, 5 ; -> baud rate index
   783 00010166 80E41F              <1> 	and	ah, 1Fh ; communication parameters except baud rate
   784 00010169 8A81[D3010100]      <1> 	mov	al, [ecx+b_div_tbl]
   785 0001016F 6689C1              <1> 	mov	cx, ax
   786 00010172 E896FFFFFF          <1> 	call	sp_i3
   787 00010177 6689C1              <1> 	mov	cx, ax ; CL = Line status, CH = Modem status
   788 0001017A A880                <1> 	test	al, 80h
   789 0001017C 740F                <1> 	jz	short sp_setp2
   790 0001017E C603E3              <1>         mov     byte [ebx], 0E3h ; Reset to initial value (11100011b)
   791                              <1> stp_dnr_err:
   792 00010181 C705[C8030300]0F00- <1> 	mov	dword [u.error], ERR_DEV_NOT_RDY ; 'device not ready !'
   792 00010189 0000                <1>
   793                              <1> 	; CL = Line status, CH = Modem status
   794 0001018B F9                  <1> 	stc
   795 0001018C C3                  <1> 	retn
   796                              <1> sp_setp2:
   797 0001018D 80FE02              <1> 	cmp	dh, 2 ; COM2 (2F?h)
   798 00010190 0F8649FFFFFF        <1>         jna     sp_i6 
   799                              <1> 		      ; COM1 (3F?h)
   800                              <1> sp_i5: 
   801                              <1> 	; 07/11/2015
   802                              <1> 	; 26/10/2015
   803                              <1> 	; 29/06/2015
   804                              <1> 	;
   805                              <1> 	;; COM1 - enabling IRQ 4
   806 00010196 9C                  <1> 	pushf
   807 00010197 FA                  <1> 	cli
   808 00010198 66BAFC03            <1> 	mov	dx, 3FCh   		; modem control register
   809 0001019C EC                  <1> 	in	al, dx 	   		; read register
   810 0001019D EB00                <1> 	JMP	$+2			; I/O DELAY
   811 0001019F 0C08                <1> 	or	al, 8      		; enable bit 3 (OUT2)
   812 000101A1 EE                  <1> 	out	dx, al     		; write back to register
   813 000101A2 EB00                <1> 	JMP	$+2			; I/O DELAY
   814 000101A4 66BAF903            <1> 	mov	dx, 3F9h   		; interrupt enable register
   815 000101A8 EC                  <1> 	in	al, dx     		; read register
   816 000101A9 EB00                <1> 	JMP	$+2			; I/O DELAY
   817                              <1> 	;or	al, 1      		; receiver data interrupt enable and
   818 000101AB 0C03                <1> 	or	al, 3	   		; transmitter empty interrupt enable
   819 000101AD EE                  <1> 	out	dx, al 	   		; write back to register
   820 000101AE EB00                <1> 	JMP	$+2        		; I/O DELAY
   821 000101B0 E421                <1> 	in	al, 21h    		; read interrupt mask register
   822 000101B2 EB00                <1> 	JMP	$+2			; I/O DELAY
   823 000101B4 24EF                <1> 	and	al, 0EFh   		; enable IRQ 4 (COM1)
   824 000101B6 E621                <1> 	out	21h, al    		; write back to register
   825                              <1> 	;
   826                              <1> 	; 23/10/2015
   827 000101B8 B8[C8FF0000]        <1> 	mov 	eax, com1_int
   828 000101BD A3[DA010100]        <1> 	mov	[com1_irq4], eax
   829                              <1> 	; 26/10/2015
   830 000101C2 9D                  <1> 	popf
   831 000101C3 C3                  <1> 	retn
   832                              <1> 
   833                              <1> sp_invp_err:
   834 000101C4 C705[C8030300]1700- <1> 	mov	dword [u.error], ERR_INV_PARAMETER ; 'invalid parameter !' 
   834 000101CC 0000                <1>
   835 000101CE 31C9                <1> 	xor	ecx, ecx
   836 000101D0 49                  <1> 	dec	ecx ; 0FFFFh
   837 000101D1 F9                  <1> 	stc
   838 000101D2 C3                  <1> 	retn
   839                              <1> 
   840                              <1> ; 29/10/2015
   841                              <1> b_div_tbl: ; Baud rate divisor table (115200/divisor)
   842 000101D3 010C0603080401      <1> 	db 1, 12, 6, 3, 8, 4, 1
   843                              <1> 
   844                              <1> 
   845                              <1> ; 23/10/2015
   846                              <1> com1_irq4:
   847 000101DA [E2010100]          <1> 	dd dummy_retn
   848                              <1> com2_irq3:
   849 000101DE [E2010100]          <1> 	dd dummy_retn
   850                              <1> 
   851                              <1> dummy_retn:
   852 000101E2 C3                  <1> 	retn
   853                              <1> 
   854                              <1> wakeup:
   855                              <1> 	; 24/01/2016
   856 000101E3 C3                  <1> 	retn
   857                              <1> 
   858                              <1> set_working_path_x:
   859                              <1> 		; 17/10/2016 (TRDOS 386 - FFF & FNF)
   860 000101E4 66B80100            <1> 		mov	ax, 1 
   861                              <1> 			; File name is needed/forced (AL=1)
   862                              <1> 			; Change directory as temporary (AH=0)	
   863                              <1> 
   864                              <1> set_working_path_xx: ; 30/12/2017 (syschdir)
   865                              <1> 		; This is needed for preventing wrong Find Next File
   866                              <1> 		; system call after sysopen, syscreate, sysmkdir etc. 
   867                              <1> 		; Find Next File must immediate follow Find First File)
   868                              <1> 
   869 000101E8 8825[346B0100]      <1> 		mov	[FFF_Valid], ah ; 0 ; reset ; 17/10/2016
   870                              <1> 
   871                              <1> set_working_path:
   872                              <1> 		; 16/10/2016
   873                              <1> 		; 12/10/2016
   874                              <1> 		; 10/10/2016
   875                              <1> 		; 05/10/2016 - TRDOS 386 (TRDOS v2.0)
   876                              <1> 		;
   877                              <1> 		; TRDOS v1.0 (DIR.ASM, "proc_set_working_path")
   878                              <1>                 ; 27/01/2011 - 08/02/2011 
   879                              <1> 		; Set/Changes current drive, directory and file
   880                              <1> 		; depending on command tail
   881                              <1> 		; (procedure is derivated from CMD_INTR.ASM 
   882                              <1> 		; file or dir locating code of internal commands)
   883                              <1> 		; (This procedure is prepared for INT 21H file/dir 
   884                              <1> 		; functions and also to get compact code for 
   885                              <1> 		; internal mainprog -command interpreter- commands)
   886                              <1> 		; 
   887                              <1> 		; INPUT: DS:SI -> Command tail (ASCIIZ string)
   888                              <1> 		; AL = 0 -> any, AL > 0 -> file name is forced
   889                              <1> 		; AH = CD -> Change directory permanently 
   890                              <1> 		; AH <> CD -> Change directory as temporary    
   891                              <1> 		; 
   892                              <1> 		; OUTPUT: ES=DS, FindFile structure has been set
   893                              <1> 		;        RUN_CDRV points previous current drive  
   894                              <1> 		;        DS:SI = FindFile structure address
   895                              <1> 		;        (DS=CS)       
   896                              <1> 		;        AX, BX, CX, DX, DI will be changed
   897                              <1> 		;   cf = 1 -> Error code in AX (AL)
   898                              <1> 		;        stc & AX = 0 -> Bad command or path name 
   899                              <1> 		; -----------------------------------------------
   900                              <1> 		;
   901                              <1> 		; TRDOS 386 (05/10/2016)
   902                              <1> 		; INPUT:
   903                              <1> 		;	ESI = File/Directory Path (ASCIIZ string)
   904                              <1> 		;             address in user's memory space
   905                              <1> 		;       AL = 0 -> any
   906                              <1> 		;       AL > 0 -> file name is forced
   907                              <1> 		;       AH = CD -> change directory as permanent
   908                              <1> 		;       AH <> CD -> change directory as temporary
   909                              <1> 		; 
   910                              <1> 		; OUTPUT:
   911                              <1> 		;	FindFile structure has been set
   912                              <1> 		;       RUN_CDRV points previous current drive  
   913                              <1> 		;       ESI = FindFile_Name address ; 12/10/2016
   914                              <1> 		;
   915                              <1> 		;       cf = 1 -> Error code in EAX (AL)
   916                              <1> 		;       stc & EAX = 0 -> Bad command or path name
   917                              <1> 		;  
   918                              <1> 		; Modified registers: EAX, EBX, ECX, EDX, ESI, EDI
   919                              <1> 
   920 000101EE 66A3[386B0100]      <1> 		mov	[SWP_Mode], ax
   921 000101F4 A0[465F0100]        <1> 		mov	al, [Current_Drv]
   922 000101F9 30E4                <1> 		xor	ah, ah
   923 000101FB 66A3[3A6B0100]      <1> 		mov	[SWP_DRV], ax
   924                              <1> 
   925                              <1> 		; TRDOS 386 ring 3 (user's page directory)
   926                              <1> 		; to ring 0 (kernel's page directory) 
   927                              <1> 		; transfer modifications (05/10/2016).
   928                              <1> 
   929 00010201 55                  <1> 		push	ebp
   930 00010202 89E5                <1> 		mov	ebp, esp
   931                              <1> 		
   932 00010204 B980000000          <1> 		mov	ecx, 128 ; maximum path length = 128 bytes
   933 00010209 29CC                <1> 		sub	esp, ecx ; reserve 128 bytes (buffer) on stack
   934 0001020B 89E7                <1> 		mov	edi, esp ; destination address (kernel space)
   935                              <1> 		; esi = source address (virtual, in user's memory space)
   936 0001020D E89AEBFFFF          <1> 		call	transfer_from_user_buffer
   937 00010212 720A                <1> 		jc	short loc_swp_xor_retn 
   938                              <1> 		
   939 00010214 89E6                <1> 		mov	esi, esp ; temporary buffer (the path) on stack
   940                              <1> loc_swp_fchar:
   941 00010216 8A06                <1> 		mov	al, [esi]
   942 00010218 3C20                <1> 		cmp	al, 20h
   943 0001021A 7711                <1> 		ja	short loc_swp_parse_path_name
   944 0001021C 740C                <1> 		je	short loc_swp_fchar_next
   945                              <1> 
   946                              <1> loc_swp_xor_retn:
   947 0001021E 31C0                <1> 		xor	eax, eax
   948 00010220 F9                  <1> 		stc
   949                              <1> loc_swp_retn:
   950 00010221 89EC                <1> 		mov	esp, ebp
   951 00010223 5D                  <1> 		pop	ebp
   952                              <1> 
   953                              <1> 		;mov	esi, FindFile_Drv
   954 00010224 BE[28680100]        <1> 		mov	esi, FindFile_Name ; 12/10/2016
   955 00010229 C3                  <1> 		retn 
   956                              <1> 
   957                              <1> loc_swp_fchar_next:
   958 0001022A 46                  <1> 		inc	esi
   959 0001022B EBE9                <1> 		jmp	short loc_swp_fchar  
   960                              <1> 
   961                              <1> loc_swp_parse_path_name:
   962 0001022D BF[E6670100]        <1> 		mov	edi, FindFile_Drv
   963 00010232 E8B9AAFFFF          <1> 		call	parse_path_name
   964 00010237 72E8                <1> 		jc	short loc_swp_retn
   965                              <1> 
   966                              <1> loc_swp_checkfile_name:
   967 00010239 803D[386B0100]00    <1> 		cmp	byte [SWP_Mode], 0
   968 00010240 761E                <1> 		jna	short loc_swp_drv
   969                              <1> 
   970                              <1> 		; 10/10/2016 (valid file name checking)
   971 00010242 BE[28680100]        <1> 		mov	esi, FindFile_Name
   972 00010247 803E20              <1> 		cmp	byte [esi], 20h
   973 0001024A 76D2                <1> 		jna	short loc_swp_xor_retn
   974                              <1> 
   975                              <1> 		; 16/10/2016
   976 0001024C C605[376B0100]00    <1> 		mov	byte [SWP_inv_fname], 0 ; reset 
   977                              <1> 		; esi = file name address (ASCIIZ)
   978 00010253 E8858CFFFF          <1> 		call	check_filename
   979 00010258 7306                <1> 		jnc	short loc_swp_drv
   980                              <1> 
   981 0001025A FE05[376B0100]      <1> 		inc	byte [SWP_inv_fname] ; set 	
   982                              <1> loc_swp_drv:
   983 00010260 8A35[465F0100]      <1> 		mov	dh, [Current_Drv]
   984                              <1>                ;mov	[RUN_CDRV], dh
   985                              <1> 
   986 00010266 8A15[E6670100]      <1> 		mov	dl, [FindFile_Drv]
   987                              <1>                ;cmp	dl, dh
   988 0001026C 3A15[465F0100]      <1> 		cmp	dl, [Current_Drv]
   989 00010272 740D                <1> 		je	short loc_swp_change_directory
   990                              <1> 
   991 00010274 FE05[3B6B0100]      <1> 		inc	byte [SWP_DRV_chg]
   992 0001027A E8FD74FFFF          <1> 		call	change_current_drive
   993 0001027F 72A0                <1> 		jc	short loc_swp_retn ; eax = error code
   994                              <1> 		; eax = 0
   995                              <1> 
   996                              <1> loc_swp_change_directory:
   997 00010281 803D[E7670100]21    <1> 		cmp	byte [FindFile_Directory], 21h
   998 00010288 F5                  <1> 		cmc
   999 00010289 7396                <1> 		jnc	short loc_swp_retn
  1000                              <1> 
  1001 0001028B FE05[3B6B0100]      <1> 		inc	byte [SWP_DRV_chg]
  1002 00010291 FE05[C7120100]      <1> 		inc	byte [Restore_CDIR]
  1003 00010297 BE[E7670100]        <1> 		mov	esi, FindFile_Directory
  1004 0001029C 8A25[396B0100]      <1> 		mov	ah, [SWP_Mode+1] 
  1005 000102A2 E833A4FFFF          <1> 		call	change_current_directory
  1006 000102A7 0F8274FFFFFF        <1> 		jc	loc_swp_retn ; eax = error code
  1007                              <1> 
  1008                              <1> loc_swp_change_prompt_dir_string:
  1009                              <1> 		; esi = PATH_Array
  1010                              <1> 		; eax = Current Directory First Cluster
  1011                              <1> 		; edi = Logical DOS Drive Description Table	
  1012 000102AD E84DA3FFFF          <1> 		call	change_prompt_dir_str 
  1013 000102B2 29C0                <1> 		sub	eax, eax ; 0
  1014 000102B4 E968FFFFFF          <1> 		jmp	loc_swp_retn 
  1015                              <1> 
  1016                              <1> reset_working_path:
  1017                              <1> 		; 06/10/2016 - TRDOS 386 (TRDOS v2.0)
  1018                              <1> 		;
  1019                              <1> 		; TRDOS v1.0 (DIR.ASM, "proc_reset_working_path")
  1020                              <1> 		; 05/02/2011 - 08/02/2011 
  1021                              <1> 		;
  1022                              <1> 		; Restores current drive and directory 
  1023                              <1> 		; 
  1024                              <1> 		; INPUT: none
  1025                              <1> 		; OUTPUT: DL = SWP_DRV, EAX = 0 -> OK
  1026                              <1> 		;
  1027                              <1> 		;    AX = 0 -> ESI = Logical Dos Drv Desc. Table
  1028                              <1> 		;
  1029                              <1> 		;    EAX, EBX, ECX, EDX, ESI, EDI will be changed
  1030                              <1> 		;
  1031                              <1> 
  1032                              <1>   
  1033 000102B9 31C0                <1> 		xor	eax, eax
  1034 000102BB 48                  <1> 		dec	eax 
  1035                              <1> 
  1036 000102BC 668B15[3A6B0100]    <1> 		mov	dx, [SWP_DRV]
  1037 000102C3 08F6                <1> 		or	dh, dh
  1038 000102C5 742E                <1> 		jz	short loc_rwp_return
  1039                              <1> 
  1040 000102C7 3A15[465F0100]      <1> 		cmp	dl, [Current_Drv]
  1041 000102CD 7407                <1> 		je	short loc_rwp_restore_cdir
  1042                              <1> loc_rwp_restore_cdrv:
  1043 000102CF E8A874FFFF          <1> 		call	change_current_drive 
  1044 000102D4 EB10                <1> 		jmp	short loc_rwp_restore_ok
  1045                              <1> loc_rwp_restore_cdir:
  1046 000102D6 31DB                <1> 		xor	ebx, ebx
  1047 000102D8 88D7                <1> 		mov	bh, dl
  1048 000102DA BE00010900          <1> 		mov	esi, Logical_DOSDisks
  1049 000102DF 01DE                <1> 		add	esi, ebx
  1050                              <1> 
  1051 000102E1 E84D75FFFF          <1> 		call	restore_current_directory
  1052                              <1> 
  1053                              <1> loc_rwp_restore_ok:
  1054 000102E6 668B15[3A6B0100]    <1> 		mov	dx, [SWP_DRV]
  1055 000102ED 31C0                <1> 		xor	eax, eax  
  1056 000102EF 66A3[3B6B0100]      <1> 		mov	[SWP_DRV_chg], ax
  1057                              <1> loc_rwp_return:
  1058 000102F5 C3                  <1> 		retn
  1059                              <1> 
  1060                              <1> get_file_name:
  1061                              <1> 		; 15/10/2016 - TRDOS 386 (TRDOS v2.0)
  1062                              <1> 		; Convert file name 
  1063                              <1> 		;	from directory entry format
  1064                              <1>                 ; 	to (8.3) dot file name format 
  1065                              <1> 		;
  1066                              <1> 		; TRDOS v1.0 (DIR.ASM, "get_file_name")
  1067                              <1>                 ; 2005 - 09/10/2011 	
  1068                              <1> 		; INPUT: 
  1069                              <1> 		;	DS:SI -> Directory Entry Format File Name
  1070                              <1> 		;       ES:DI -> DOS Dot File Name Address
  1071                              <1> 		; OUTPUT:
  1072                              <1> 		;	DS:SI -> DOS Dot File Name Address
  1073                              <1>                 ;	ES:DI -> Directory Entry Format File Name
  1074                              <1> 		;	
  1075                              <1> 		; TRDOS 386 (15/10/2016)
  1076                              <1> 		; INPUT:
  1077                              <1> 		;	ESI = File name addr in dir entry format
  1078                              <1> 		;	EDI = Dot file name address (destination)
  1079                              <1> 		; OUTPUT: 
  1080                              <1> 		;	File name is converted and moved
  1081                              <1> 		;	to destination (as 8.3 dot filename)
  1082                              <1> 		;  
  1083                              <1> 		; Modified registers: EAX, ECX
  1084                              <1> 
  1085                              <1>                 ; 2005 (TRDOS 8086) - 2016 (TRDOS 386)
  1086                              <1>                             
  1087 000102F6 57                  <1> 		push	edi
  1088 000102F7 56                  <1> 		push	esi
  1089 000102F8 AC                  <1> 		lodsb
  1090 000102F9 3C20                <1> 		cmp	al, 20h
  1091 000102FB 762A                <1> 		jna	short pass_gfn_ext
  1092 000102FD 56                  <1> 		push	esi
  1093 000102FE AA                  <1> 		stosb
  1094 000102FF B907000000          <1> 		mov	ecx, 7
  1095                              <1> loc_gfn_next_char:
  1096 00010304 AC                  <1> 		lodsb
  1097 00010305 3C20                <1> 		cmp	al, 20h
  1098 00010307 7603                <1> 		jna	short pass_gfn_fn
  1099 00010309 AA                  <1> 		stosb
  1100 0001030A E2F8                <1> 		loop	loc_gfn_next_char
  1101                              <1> pass_gfn_fn:
  1102 0001030C 5E                  <1> 		pop	esi
  1103 0001030D 83C607              <1> 		add	esi, 7
  1104 00010310 AC                  <1> 		lodsb
  1105 00010311 3C20                <1> 		cmp	al, 20h
  1106 00010313 7612                <1> 		jna	short pass_gfn_ext
  1107 00010315 B42E                <1> 		mov	ah, '.'
  1108 00010317 86E0                <1> 		xchg	ah, al
  1109 00010319 66AB                <1> 		stosw
  1110 0001031B AC                  <1> 		lodsb
  1111 0001031C 3C20                <1> 		cmp	al, 20h
  1112 0001031E 7607                <1> 		jna	short pass_gfn_ext
  1113 00010320 AA                  <1> 		stosb
  1114 00010321 AC                  <1> 		lodsb
  1115 00010322 3C20                <1> 		cmp	al, 20h
  1116 00010324 7601                <1> 		jna	short pass_gfn_ext
  1117 00010326 AA                  <1> 		stosb
  1118                              <1> pass_gfn_ext:		
  1119 00010327 30C0                <1> 		xor	al, al
  1120 00010329 AA                  <1> 		stosb
  1121 0001032A 5E                  <1> 		pop	esi
  1122 0001032B 5F                  <1> 		pop	edi
  1123 0001032C C3                  <1> 		retn
  1124                              <1> 
  1125                              <1> set_hardware_int_vector:
  1126                              <1> 		; 18/03/2017
  1127                              <1> 		; 03/03/2017
  1128                              <1> 		; 28/02/2017 - TRDOS 386 (TRDOS v2.0)
  1129                              <1> 		;
  1130                              <1> 		; SET/RESET HARDWARE INTERRUPT GATE
  1131                              <1> 		;
  1132                              <1> 		; Changes interrupt gate descriptor table
  1133                              <1> 		; (without changing default interrupt list)
  1134                              <1> 		;
  1135                              <1> 		; INPUT:
  1136                              <1> 		;	AL = IRQ number (0 to 15)
  1137                              <1> 		;	AH > 0 -> set
  1138                              <1> 		;	AH = 0 -> reset
  1139                              <1> 		;	
  1140                              <1> 		; Modified registers: eax, ebx, edx, edi 
  1141                              <1> 		;
  1142                              <1> 		
  1143 0001032D C0E002              <1> 		shl	al, 2 ; IRQ number * 4
  1144 00010330 0FB6D8              <1> 		movzx	ebx, al
  1145                              <1> 
  1146 00010333 08E4                <1> 		or	ah, ah
  1147 00010335 7508                <1> 		jnz	short shintv_1 ; set (for user call service)
  1148                              <1> 		
  1149                              <1> 		; 18/03/2017
  1150 00010337 81C3[C41C0100]      <1> 		add	ebx, IRQ_list ; reset to default interrupt list
  1151 0001033D EB06                <1> 		jmp	short shintv_2
  1152                              <1> shintv_1:
  1153 0001033F 81C3[66030100]      <1> 		add	ebx, IRQ_u_list
  1154                              <1> shintv_2:	
  1155 00010345 8B13                <1> 		mov	edx, [ebx] ; IRQ handler address
  1156                              <1> 		
  1157                              <1> 		; 03/03/2017
  1158 00010347 D0E0                <1> 		shl	al, 1 ; IRQ number * 8 
  1159                              <1> 		; 18/03/2017
  1160 00010349 0FB6F8              <1> 		movzx	edi, al 
  1161 0001034C 81C7[985C0100]      <1> 		add	edi, idt + (8*32) ; IRQ 0 offset = idt + 256
  1162                              <1> 		
  1163 00010352 89D0                <1> 		mov	eax, edx ; IRQ handler address
  1164 00010354 BB00000800          <1> 		mov	ebx, 80000h
  1165                              <1> 
  1166                              <1> 		;mov	edx, eax
  1167 00010359 66BA008E            <1> 		mov	dx, 8E00h
  1168 0001035D 6689C3              <1> 		mov	bx, ax
  1169 00010360 89D8                <1> 		mov	eax, ebx ; /* selector = 0x0008 = cs */
  1170                              <1>        			         ; /* interrupt gate - dpl=0, present */
  1171 00010362 AB                  <1> 		stosd	; selector & offset bits 0-15 	
  1172 00010363 8917                <1> 		mov	[edi], edx ; attributes & offset bits 16-23
  1173                              <1> 
  1174 00010365 C3                  <1> 		retn
  1175                              <1> IRQ_u_list:
  1176                              <1> 		; 28/02/2017
  1177 00010366 [CF080000]          <1> 		dd	timer_int
  1178 0001036A [43100000]          <1> 		dd	kb_int
  1179 0001036E [B10A0000]          <1> 		dd	irq2
  1180 00010372 [A6030100]          <1> 		dd	IRQ_service3
  1181 00010376 [B0030100]          <1> 		dd	IRQ_service4
  1182 0001037A [BA030100]          <1> 		dd	IRQ_service5
  1183 0001037E [E5480000]          <1> 		dd	fdc_int	
  1184 00010382 [C4030100]          <1> 		dd	IRQ_service7
  1185 00010386 [3A0A0000]          <1> 		dd	rtc_int
  1186 0001038A [CE030100]          <1> 		dd	IRQ_service9
  1187 0001038E [D8030100]          <1> 		dd	IRQ_service10
  1188 00010392 [E2030100]          <1> 		dd	IRQ_service11
  1189 00010396 [EC030100]          <1> 		dd	IRQ_service12
  1190 0001039A [F6030100]          <1> 		dd	IRQ_service13
  1191 0001039E [98520000]          <1> 		dd	hdc1_int
  1192 000103A2 [BF520000]          <1> 		dd	hdc2_int
  1193                              <1> 
  1194                              <1> 		; 03/03/2017
  1195                              <1> 		; 27/02/2017
  1196                              <1> IRQ_service3:
  1197 000103A6 36C605[FE700100]03  <1> 		mov	byte [ss:IRQnum], 3
  1198 000103AE EB4E                <1> 		jmp	short IRQ_service
  1199                              <1> IRQ_service4:
  1200 000103B0 36C605[FE700100]04  <1> 		mov	byte [ss:IRQnum], 4
  1201 000103B8 EB44                <1> 		jmp	short IRQ_service
  1202                              <1> IRQ_service5:
  1203 000103BA 36C605[FE700100]05  <1> 		mov	byte [ss:IRQnum], 5
  1204 000103C2 EB3A                <1> 		jmp	short IRQ_service
  1205                              <1> IRQ_service7:
  1206 000103C4 36C605[FE700100]07  <1> 		mov	byte [ss:IRQnum], 7
  1207 000103CC EB30                <1> 		jmp	short IRQ_service
  1208                              <1> IRQ_service9:
  1209 000103CE 36C605[FE700100]09  <1> 		mov	byte [ss:IRQnum], 9
  1210 000103D6 EB26                <1> 		jmp	short IRQ_service
  1211                              <1> IRQ_service10:
  1212 000103D8 36C605[FE700100]0A  <1> 		mov	byte [ss:IRQnum], 10
  1213 000103E0 EB1C                <1> 		jmp	short IRQ_service
  1214                              <1> IRQ_service11:
  1215 000103E2 36C605[FE700100]0B  <1> 		mov	byte [ss:IRQnum], 11
  1216 000103EA EB12                <1> 		jmp	short IRQ_service
  1217                              <1> IRQ_service12:
  1218 000103EC 36C605[FE700100]0C  <1> 		mov	byte [ss:IRQnum], 12
  1219 000103F4 EB08                <1> 		jmp	short IRQ_service
  1220                              <1> IRQ_service13:
  1221 000103F6 36C605[FE700100]0D  <1> 		mov	byte [ss:IRQnum], 13
  1222                              <1> 		;jmp	short IRQ_service
  1223                              <1> IRQ_service:
  1224                              <1> 		; 13/06/2017
  1225                              <1> 		; 11/06/2017
  1226                              <1> 		; 10/06/2017
  1227                              <1> 		; 01/03/2017, 04/03/2017
  1228                              <1> 		; 27/02/2017, 28/02/2017
  1229 000103FE 1E                  <1> 		push	ds
  1230 000103FF 06                  <1> 		push	es
  1231 00010400 0FA0                <1> 		push	fs
  1232 00010402 0FA8                <1> 		push	gs
  1233                              <1> 
  1234 00010404 60                  <1> 		pushad	; eax,ecx,edx,ebx,esp,ebp,esi,edi
  1235 00010405 66B91000            <1> 		mov     cx, KDATA
  1236 00010409 8ED9                <1>         	mov     ds, cx
  1237 0001040B 8EC1                <1>         	mov     es, cx
  1238 0001040D 8EE1                <1>         	mov     fs, cx
  1239 0001040F 8EE9                <1>         	mov     gs, cx
  1240                              <1> 
  1241 00010411 0F20D8              <1> 		mov	eax, cr3
  1242 00010414 A3[FA700100]        <1> 		mov	[IRQ_cr3], eax
  1243                              <1> 
  1244 00010419 A1[805E0100]        <1> 		mov	eax, [k_page_dir]
  1245 0001041E 0F22D8              <1> 		mov	cr3, eax 
  1246                              <1> 
  1247 00010421 A0[FE700100]        <1> 		mov	al, [IRQnum]
  1248                              <1> 
  1249                              <1> 		;mov	cl, [sysflg]
  1250                              <1> 		;mov	[u.r_mode], cl  ; system (0) or user mode (FFh) 
  1251                              <1> IRQsrv_0:
  1252 00010426 0FB6D8              <1> 		movzx	ebx, al
  1253 00010429 8A9B[FC1B0100]      <1> 		mov	bl, [ebx+IRQenum] ; IRQ (available) index number + 1
  1254                              <1> 		; 01/03/2017
  1255 0001042F FECB                <1> 		dec	bl  ; IRQ index number, 0 to 8
  1256 00010431 0F8807010000        <1> 		js	IRQsrv_5 ; not available to use here!?
  1257                              <1> 		;		 
  1258 00010437 80BB[C4700100]80    <1> 		cmp	byte [ebx+IRQ.method], 80h ; using by a dev or kernel? 
  1259 0001043E 7205                <1> 		jb	short IRQsrv_1 ; no
  1260                              <1> 
  1261                              <1> 		; If the IRQ service is already owned by TRDOS 386 kernel
  1262                              <1> 		;	 or a Device driver
  1263                              <1> 		; we need to call 'dev_IRQ_service'
  1264                              <1> 
  1265                              <1> 		; IRQ number in AL
  1266 00010440 E866020000          <1> 		call	dev_IRQ_service	 ; IRQ service for device drivers	
  1267                              <1> 		; IRQ number in AL
  1268                              <1> IRQsrv_1:		
  1269                              <1> 		; check user callback service status
  1270                              <1> 		; AL = IRQ number
  1271                              <1> 		; EBX = IRQ (Available) Index number
  1272                              <1> 
  1273 00010445 A2[D7030300]        <1> 		mov	[u.irqwait], al ; set waiting IRQ flag
  1274                              <1> 
  1275 0001044A 8A83[B2700100]      <1> 		mov	al, [ebx+IRQ.owner]
  1276 00010450 20C0                <1> 		and	al, al
  1277 00010452 0F84E6000000        <1> 		jz	IRQsrv_5 ; it is not owned by a user/proc
  1278                              <1> 
  1279                              <1> 		; 03/03/2017
  1280 00010458 89DA                <1> 		mov	edx, ebx
  1281 0001045A C0E202              <1> 		shl	dl, 2
  1282 0001045D 8B92[D6700100]      <1> 		mov	edx, [edx+IRQ.addr] ; S.R.B. or Callback service addr
  1283                              <1> 		
  1284 00010463 8AA3[C4700100]      <1> 		mov	ah, [ebx+IRQ.method]
  1285 00010469 F6C401              <1> 		test	ah, 1
  1286 0001046C 7534                <1> 		jnz	short IRQsrv_4 ; Callback service method
  1287                              <1> 
  1288                              <1> 		; Signal Response Byte method
  1289                              <1> 		;mov	edx, [edx+IRQ.addr] ; Signal Response Byte address
  1290                              <1> 		;			    ; (Physical address, non-swappable) 	
  1291 0001046E 80E402              <1> 		and	ah, 2 ; bit 1, (S.R.B.) counter (auto increment) method
  1292 00010471 8AA3[CD700100]      <1> 		mov	ah, [ebx+IRQ.srb] ; Signal Response Byte value
  1293 00010477 7408                <1> 		jz	short IRQsrv_2 ; fixed S.R.B. value
  1294                              <1> 		; counter method (auto increment)
  1295 00010479 FEC4                <1> 		inc	ah
  1296 0001047B 88A3[CD700100]      <1> 		mov	[ebx+IRQ.srb], ah ; next (count) number
  1297                              <1> IRQsrv_2:
  1298 00010481 8822                <1> 		mov	[edx], ah ; put S.R.B. val to the user's S.R.B. addr
  1299 00010483 C605[D7030300]00    <1> 		mov	byte [u.irqwait], 0 ; clear waiting IRQ flag
  1300                              <1> 
  1301 0001048A 3A05[B3030300]      <1> 		cmp	al, [u.uno]
  1302 00010490 0F84A8000000        <1> 		je	IRQsrv_5 ; the owner is current user/process
  1303                              <1> IRQsrv_3:
  1304                              <1> 		; the owner is not current user/process
  1305                              <1> 		; AL = process number
  1306 00010496 B202                <1> 		mov	dl, 2 ; priority, 2 = event (high)	
  1307 00010498 E837FAFFFF          <1> 		call	set_run_sequence
  1308                              <1> 
  1309                              <1> 		; [u.irqwait] = waiting IRQ number for callback service
  1310                              <1> 
  1311 0001049D E99C000000          <1> 		jmp	IRQsrv_5
  1312                              <1> IRQsrv_4:
  1313 000104A2 3A05[B3030300]      <1> 		cmp	al, [u.uno]  ; is the owner is current user/process?
  1314 000104A8 75EC                <1> 		jne	short IRQsrv_3 ; no !
  1315                              <1> 
  1316                              <1> 		; Check if an IRQ callback service already in progress
  1317 000104AA 803D[D8030300]00    <1> 		cmp	byte [u.r_lock], 0
  1318 000104B1 0F8787000000        <1> 		ja	IRQsrv_5 ; nothing to do !  
  1319                              <1> 				     ; (we need to complete prev callback)
  1320 000104B7 803D[D4030300]00    <1> 		cmp	byte [u.t_lock], 0
  1321 000104BE 777E                <1> 		ja	short IRQsrv_5 ; nothing to do !  
  1322                              <1> 				     ; (we need to complete timer callback)
  1323                              <1> 
  1324                              <1> 		; 04/03/2017
  1325 000104C0 C605[D7030300]00    <1> 		mov	byte [u.irqwait], 0 ; reset/clear waiting IRQ flag
  1326                              <1> 
  1327 000104C7 FE05[D8030300]      <1> 		inc	byte [u.r_lock] ; 'IRQ callback service in progress' flag
  1328                              <1> 
  1329 000104CD 8A0D[5B030300]      <1> 		mov	cl, [sysflg]   ; (system call) mode flag (kernel/user)
  1330 000104D3 880D[D9030300]      <1> 		mov	[u.r_mode], cl ; system mode (0) or user mode (FFh)
  1331                              <1> 
  1332                              <1> 		; 
  1333 000104D9 8B2D[1C5E0100]      <1> 		mov	ebp, [tss.esp0] ; kernel stack address (for ring 0)
  1334 000104DF 83ED14              <1> 		sub	ebp, 20		; eip, cs, eflags, esp, ss
  1335 000104E2 892D[5C030300]      <1> 	 	mov	[u.sp], ebp
  1336 000104E8 8925[60030300]      <1> 		mov	[u.usp], esp
  1337                              <1> 
  1338                              <1> 		;or	word [ebp+8], 200h ; 22/01/2017, force enabling interrupts
  1339                              <1> 
  1340 000104EE 8B44241C            <1> 		mov	eax, [esp+28] ; pushed eax
  1341 000104F2 A3[64030300]        <1> 		mov	[u.r0], eax
  1342                              <1> 
  1343 000104F7 E81AE7FFFF          <1> 		call	wswap ; save user's registers & status
  1344                              <1> 
  1345                              <1> 		; software int is in ring 0 but IRQ handler must return to ring 3
  1346                              <1> 		; so, ring 3 return address and stack registers
  1347                              <1> 		; (eip, cs, eflags, esp, ss) 
  1348                              <1> 		; must be copied to IRQ handler return
  1349                              <1> 		; eip will be replaced by callback service routine address
  1350                              <1> 
  1351 000104FC C605[5B030300]FF    <1> 		mov	byte [sysflg], 0FFh ; user mode
  1352                              <1> 
  1353                              <1> 		; system mode (system call)
  1354                              <1> 		;mov	ebp, [u.sp] ; EIP (u), CS (UCODE), EFLAGS (u),
  1355                              <1> 				    ; ESP (u), SS (UDATA)
  1356                              <1> 
  1357 00010503 8B4510              <1> 		mov	eax, [ebp+16]	; SS (UDATA)
  1358 00010506 89E6                <1> 		mov	esi, esp
  1359 00010508 50                  <1> 		push	eax
  1360 00010509 50                  <1> 		push	eax
  1361 0001050A 89E7                <1> 		mov	edi, esp
  1362 0001050C 893D[60030300]      <1> 		mov	[u.usp], edi
  1363 00010512 B908000000          <1> 		mov	ecx, ((ESPACE/4) - 4) ; except DS, ES, FS, GS
  1364 00010517 F3A5                <1> 		rep	movsd
  1365 00010519 B104                <1> 		mov	cl, 4	
  1366 0001051B F3AB                <1> 		rep	stosd
  1367 0001051D 893D[5C030300]      <1> 		mov	[u.sp], edi
  1368 00010523 89EE                <1> 		mov	esi, ebp
  1369 00010525 B105                <1> 		mov	cl, 5 ; EIP (u), CS (UCODE), EFLAGS (u), ESP (u), SS (UDATA)
  1370 00010527 F3A5                <1> 		rep	movsd
  1371                              <1> 		;
  1372                              <1> 
  1373 00010529 8B0D[B8030300]      <1> 		mov	ecx, [u.pgdir]
  1374 0001052F 890D[FA700100]      <1> 		mov	[IRQ_cr3], ecx
  1375                              <1> 
  1376                              <1> set_IRQ_callback_addr:
  1377                              <1> 		;
  1378                              <1> 		; This routine sets return address
  1379                              <1> 		; to start of user's interrupt
  1380                              <1> 		; service (callback) address
  1381                              <1> 		;
  1382                              <1> 		; INPUT:
  1383                              <1> 		;	EDX = callback routine/service address
  1384                              <1> 		;	      (virtual, not physical address!)	
  1385                              <1> 		;	[u.sp] = kernel stack, points to
  1386                              <1> 		;		 user's EIP,CS,EFLAGS,ESP,SS
  1387                              <1> 		;		 registers.
  1388                              <1> 		; OUTPUT:
  1389                              <1> 		;	EIP (user) = callback (service) address
  1390                              <1> 		;	CS (user) = UCODE
  1391                              <1> 		;	EFLAGS (user) = flags before callback 	 
  1392                              <1> 		;       ESP (user) = ESP-4 (user, before callback) 
  1393                              <1> 		;	[ESP](user) = EIP (user) before callback
  1394                              <1> 		;
  1395                              <1> 		; Note: If CPU was in user mode while entering 
  1396                              <1> 		;	the timer interrupt service routine,
  1397                              <1> 		;	'IRET' will get return to callback routine
  1398                              <1> 		;	immediately. If CPU was in system/kernel mode  
  1399                              <1> 		;	'iret' will get return to system call and
  1400                              <1> 		;	then, callback routine will be return address
  1401                              <1> 		;	from system call. (User's callback/service code
  1402                              <1> 		;	will be able to return to normal return address
  1403                              <1> 		;	via a 'sysrele' system call at the end.) 
  1404                              <1> 		;
  1405                              <1> 		; Note: User's IRQ callback service code must be ended
  1406                              <1> 		;	with a 'sysrele' system call !
  1407                              <1> 		;
  1408                              <1> 		;	For example:
  1409                              <1> 		;
  1410                              <1> 		;	audio_IRQ_callback:
  1411                              <1> 		;	    ...	 
  1412                              <1> 		;	    <load DMA buffer with audio data>
  1413                              <1> 		;	    ...
  1414                              <1> 		;	    mov eax, 39 ; 'sysrele'
  1415                              <1> 		;	    int 40h ; TRDOS 386 system call (interrupt)		
  1416                              <1> 		;
  1417                              <1> 		
  1418                              <1> 		;mov	edx, [edx+IRQ.addr] ; Callback service address
  1419                              <1> 		;			    ; (Virtual address)
  1420                              <1> 		
  1421 00010535 8B2D[5C030300]      <1> 		mov	ebp, [u.sp]; kernel's stack, points to EIP (user)
  1422 0001053B 895500              <1> 		mov	[ebp], edx
  1423                              <1> IRQsrv_5:
  1424                              <1> 		; EOI & return
  1425                              <1> 		; 01/08/2020
  1426                              <1> 		; 11/06/2017
  1427                              <1> 		; 10/06/2017 
  1428                              <1> 		;mov	al, [IRQnum]
  1429 0001053E B020                <1> 		mov	al, 20h ; 01/08/2020
  1430 00010540 FA                  <1> 		cli
  1431                              <1> 		;cmp	al, 7
  1432 00010541 803D[FE700100]07    <1> 		cmp	byte [IRQnum], 7 ; 01/08/2020	
  1433 00010548 7602                <1> 		jna	short IRQsrv_6
  1434                              <1> 		;
  1435                              <1> 		;;mov	al, EOI	; end of interrupt
  1436                              <1> 		;mov	al, 20h ; 01/08/2020
  1437                              <1> 		;cli		; disable interrupts till stack cleared
  1438                              <1> 		;out	INTB00, al ; For controll2 #2
  1439 0001054A E6A0                <1> 		out	0A0h, al
  1440                              <1> IRQsrv_6:
  1441                              <1> 		;mov	byte [IRQnum], 0 ; reset
  1442                              <1> 		;;mov	al, EOI	; end of interrupt
  1443                              <1> 		;mov	al, 20h ; 01/08/2020
  1444                              <1> 		;cli		; disable interrupts till stack cleared
  1445                              <1> 		;out	INTA00, al ; end of interrupt to 8259 - 1
  1446 0001054C E620                <1> 		out	20h, al	
  1447                              <1> IRQsrv_7:	
  1448                              <1> 		;; 13/06/2017
  1449                              <1> 		;or	word [ebp+8], 200h ; force enabling interrupts
  1450                              <1> 		;
  1451 0001054E 8B0D[FA700100]      <1> 		mov 	ecx, [IRQ_cr3]	; previous content of cr3 register
  1452 00010554 0F22D9              <1>  		mov	cr3, ecx	; restore cr3 register content
  1453                              <1> 		;
  1454 00010557 61                  <1> 		popad ; edi,esi,ebp,(icrement esp by 4),ebx,edx,ecx,eax
  1455                              <1> 		;
  1456 00010558 0FA9                <1> 		pop	gs
  1457 0001055A 0FA1                <1> 		pop	fs
  1458 0001055C 07                  <1> 		pop	es
  1459 0001055D 1F                  <1> 		pop	ds
  1460                              <1> 		;
  1461 0001055E CF                  <1> 		iretd	; return from interrupt
  1462                              <1> 
  1463                              <1> get_device_number:
  1464                              <1> 		; 08/10/2016
  1465                              <1> 		; 07/10/2016 - TRDOS 386 (TRDOS v2.0)
  1466                              <1> 		;
  1467                              <1> 		; This procedure compares name of requested
  1468                              <1> 		; device with kernel device names and
  1469                              <1> 		; installable device names. If names match, 
  1470                              <1> 		; the relevant device index (entry) number 
  1471                              <1> 		; will be returned the caller (sysopen) 
  1472                              <1> 		; for the requested device.
  1473                              <1> 		;
  1474                              <1> 		; NOTE: Installable device drivers must
  1475                              <1> 		; be loaded before using 'sysopen'
  1476                              <1> 		; (opendev) system call.
  1477                              <1> 		;
  1478                              <1> 		; INPUT:
  1479                              <1> 		;    ESI = device name address (ASCIIZ)
  1480                              <1> 		;         (in kernel's memory space)  
  1481                              <1>    		;    max name length = 8 without '/dev/')
  1482                              <1> 		;    Device name will be capitalized 
  1483                              <1> 		;    and if there is, '/dev/' will be
  1484                              <1> 		;    removed from name before comparising)
  1485                              <1> 		;
  1486                              <1> 		; OUTPUT:
  1487                              <1> 		;    cf = 0 -> 
  1488                              <1> 		;      EAX (AL) = device entry/index number 	 	
  1489                              <1> 		;    cf = 1 -> device not found (installed)
  1490                              <1> 		;	       or invalid device name
  1491                              <1> 		;	       (AL=0)
  1492                              <1> 		;    device_name = device name address (asciiz)
  1493                              <1> 			;
  1494                              <1> 		; Modified registers: EAX, EBX, ESI, EDI
  1495                              <1> 
  1496 0001055F BF[3D6B0100]        <1> 		mov	edi, device_name
  1497 00010564 E805010000          <1> 		call 	lodsb_capitalize
  1498 00010569 88C4                <1> 		mov	ah, al
  1499 0001056B 3C2F                <1> 		cmp	al, '/'
  1500 0001056D 750E                <1> 		jne	short gdn_1
  1501 0001056F BF[3D6B0100]        <1> 		mov	edi, device_name
  1502 00010574 E8F5000000          <1> 		call 	lodsb_capitalize
  1503                              <1> gdn_0:
  1504 00010579 20C0                <1> 		and	al, al ; 0 ?
  1505 0001057B 7420                <1> 		jz	short gdn_err ; null name after '/'
  1506                              <1> gdn_1:
  1507 0001057D 3C44                <1> 		cmp	al, 'D'
  1508 0001057F 7517                <1> 		jne	short gdn_2
  1509 00010581 E8E8000000          <1> 		call 	lodsb_capitalize
  1510 00010586 3C45                <1> 		cmp	al, 'E'
  1511 00010588 750E                <1> 		jne	short gdn_2
  1512 0001058A E8DF000000          <1> 		call 	lodsb_capitalize
  1513 0001058F 3C56                <1> 		cmp	al, 'V'
  1514 00010591 7505                <1> 		jne	short gdn_2			
  1515 00010593 AC                  <1> 		lodsb
  1516 00010594 3C2F                <1> 		cmp	al, '/'
  1517 00010596 740D                <1> 		je	short gdn_4
  1518                              <1> gdn_2:
  1519 00010598 80FC2F              <1> 		cmp	ah, '/'
  1520 0001059B 750F                <1> 		jne	short gdn_5
  1521                              <1> gdn_err:		
  1522                              <1> 		; invalid device name or device not found
  1523 0001059D 31C0                <1> 		xor	eax, eax ; 0
  1524 0001059F F9                  <1> 		stc
  1525 000105A0 C3                  <1> 		retn
  1526                              <1> gdn_3:
  1527 000105A1 3C2F                <1> 		cmp	al, '/'
  1528 000105A3 7507                <1> 		jne	short gdn_5
  1529                              <1> gdn_4:
  1530 000105A5 BF[3D6B0100]        <1> 		mov	edi, device_name
  1531 000105AA EB04                <1> 		jmp	short gdn_6
  1532                              <1> gdn_5:
  1533 000105AC 3C00                <1> 		cmp	al, 0
  1534 000105AE 7419                <1> 		je	short gdn_7
  1535                              <1> gdn_6:
  1536 000105B0 E8B9000000          <1> 		call lodsb_capitalize
  1537 000105B5 81FF[456B0100]      <1> 		cmp	edi, device_name + 8
  1538 000105BB 72E4                <1> 		jb	short gdn_3
  1539 000105BD 3C00                <1> 		cmp	al, 0
  1540 000105BF 75DC                <1> 		jne	short gdn_err
  1541 000105C1 81FF[3E6B0100]      <1> 		cmp	edi, device_name + 1
  1542 000105C7 76D4                <1> 		jna	short gdn_err ; null name after '/'
  1543                              <1> gdn_7:
  1544 000105C9 AA                  <1> 		stosb
  1545                              <1> 		; zero padding ("NAME",0,0,0,0)
  1546 000105CA 81FF[456B0100]      <1> 		cmp	edi, device_name + 8
  1547 000105D0 72F7                <1> 		jb	short gdn_7
  1548                              <1> gdn_8:
  1549                              <1> 		; search for kernel device names
  1550 000105D2 BE[3D6B0100]        <1> 		mov	esi, device_name 
  1551 000105D7 BF[E2190100]        <1> 		mov	edi, KDEV_NAME
  1552 000105DC 31C0                <1> 		xor	eax, eax
  1553                              <1> gdn_9:
  1554 000105DE A7                  <1> 		cmpsd	
  1555 000105DF 7505                <1> 		jne	short gdn_10
  1556 000105E1 A7                  <1> 		cmpsd
  1557 000105E2 7503                <1> 		jne	short gdn_11
  1558 000105E4 EB2B                <1> 		jmp	short gdn_17 ; match
  1559                              <1> gdn_10:
  1560 000105E6 A7                  <1> 		cmpsd  ; add esi, 4 & add edi, 4
  1561                              <1> gdn_11:
  1562 000105E7 BE[3D6B0100]        <1> 		mov	esi, device_name
  1563 000105EC FEC0                <1> 		inc	al
  1564 000105EE 3C16                <1> 		cmp	al, NumOfKernelDevNames
  1565 000105F0 72EC                <1> 		jb	short gdn_9
  1566                              <1> gdn_12:
  1567                              <1> 		; search for installable device names
  1568                              <1> 		; esi = offset device_name 
  1569 000105F2 BF[686B0100]        <1> 		mov	edi, IDEV_NAME
  1570 000105F7 28C0                <1> 		sub	al, al ; 0
  1571                              <1> gdn_13:
  1572 000105F9 A7                  <1> 		cmpsd	
  1573 000105FA 7505                <1> 		jne	short gdn_14
  1574 000105FC A7                  <1> 		cmpsd
  1575 000105FD 7503                <1> 		jne	short gdn_15
  1576 000105FF EB3F                <1> 		jmp	short gdn_19 ; match
  1577                              <1> gdn_14:
  1578 00010601 A7                  <1> 		cmpsd  ; add esi, 4 & add edi, 4
  1579                              <1> gdn_15:
  1580 00010602 BE[3D6B0100]        <1> 		mov	esi, device_name
  1581 00010607 FEC0                <1> 		inc	al
  1582 00010609 3C08                <1> 		cmp	al, NumOfInstallableDevices
  1583 0001060B 72EC                <1> 		jb	short gdn_13
  1584                              <1> 
  1585                              <1> gdn_16: 	; error: invalid device name (not found) !
  1586 0001060D 30C0                <1> 		xor	al, al
  1587 0001060F F9                  <1> 		stc
  1588 00010610 C3                  <1> 		retn
  1589                              <1> 
  1590                              <1> gdn_17:		; name match (with one of kernel device names)
  1591                              <1> 		;
  1592                              <1> 		; convert KDEV_NAME index to 
  1593                              <1> 		; KDEV_NUMBER index
  1594                              <1> 		; (different names are used for same devices)
  1595                              <1> 		; (example: "COM1" & "TTY8" = device number 18) 
  1596 00010611 89C3                <1> 		mov	ebx, eax ; < 256
  1597 00010613 8A83[921A0100]      <1> 		mov	al, [KDEV_NUMBER+ebx]
  1598                              <1> 
  1599                              <1> 		; check if empty dev entry in the list
  1600 00010619 80B8[EC6C0100]00    <1> 		cmp	byte [DEV_OPENMODE+eax], 0
  1601 00010620 771B                <1> 		ja	short gdn_18 ; it must be already set
  1602                              <1> 
  1603                              <1> 		; (re)set device name and access flags
  1604                              <1> 		; (remain open work will be easy after that)
  1605                              <1> 		; (NOTE: here, data will be copied to bss section)
  1606 00010622 88C3                <1> 		mov	bl, al
  1607 00010624 83EF08              <1> 		sub	edi, 8 ; kernel device name address (data)
  1608 00010627 66C1E302            <1> 		shl	bx, 2 
  1609 0001062B 89BB[0A6D0100]      <1> 		mov	[DEV_NAME_PTR+ebx], edi ; (all) device names
  1610 00010631 8A98[E81B0100]      <1> 		mov	bl, [KDEV_ACCESS+eax] ; kernel dev list (data)
  1611 00010637 8898[386C0100]      <1> 		mov	[DEV_ACCESS+eax], bl ; (all) device list (bss)
  1612                              <1> gdn_18:
  1613 0001063D FEC0                <1> 		inc	al ; 1 to NumOfKernelDevNames (<=7Fh)
  1614                              <1> 		; eax = device index/entry number
  1615 0001063F C3                  <1> 		retn		
  1616                              <1> 
  1617                              <1> gdn_19:		; name match (with one of installable device names)
  1618                              <1> 		;
  1619                              <1> 		; al = 0 to NumOfInstallableDevices - 1 (<=7Fh)
  1620                              <1> 
  1621 00010640 89C3                <1> 		mov	ebx, eax
  1622 00010642 80C316              <1> 		add	bl, NumOfKernelDevices 	; < NUMOFDEVICES	
  1623                              <1> 
  1624                              <1> 		; check if empty dev entry in the list
  1625 00010645 80BB[EC6C0100]00    <1> 		cmp	byte [DEV_OPENMODE+ebx], 0
  1626 0001064C 771D                <1> 		ja	short gdn_20 ; it must be already set
  1627                              <1> 
  1628                              <1> 		; (re)set device name and access flags
  1629                              <1> 		; (remain open work will be easy after that)
  1630 0001064E 83EF08              <1> 		sub	edi, 8 ; installable device name address
  1631 00010651 66C1E302            <1> 		shl	bx, 2 ;*4
  1632 00010655 89BB[0A6D0100]      <1> 		mov	[DEV_NAME_PTR+ebx], edi ; (all) device names
  1633 0001065B 66C1EB02            <1> 		shr	bx, 2
  1634 0001065F 8A80[B06B0100]      <1> 		mov	al, [IDEV_FLAGS+eax] ; installable dev list
  1635 00010665 8883[386C0100]      <1> 		mov	[DEV_ACCESS+ebx], al ; (all) device list
  1636                              <1> gdn_20:	
  1637 0001066B 88D8                <1> 		mov	al, bl
  1638                              <1> 		; eax = device index/entry number ; < NUMOFDEVICES  
  1639 0001066D C3                  <1> 		retn
  1640                              <1> 
  1641                              <1> lodsb_capitalize:
  1642                              <1> 	; 07/10/2016 - TRDOS 386 (TRDOS v2.0)
  1643                              <1> 	; INPUT -> [esi] = character
  1644                              <1> 	;          edi = destination
  1645                              <1> 	; OUTPUT -> AL contains capitalized character
  1646                              <1> 	;	   esi = esi+1
  1647                              <1> 	;	   edi = edi+1	
  1648                              <1> 	; 
  1649 0001066E AC                  <1> 	lodsb	
  1650 0001066F 3C61                <1> 	cmp al, 61h
  1651 00010671 7206                <1>      	jb  short lodsb_cap_retn
  1652 00010673 3C7A                <1>      	cmp al, 7Ah
  1653 00010675 7702                <1>      	ja  short lodsb_cap_retn
  1654 00010677 24DF                <1>      	and al, 0DFh
  1655                              <1> lodsb_cap_retn:
  1656 00010679 AA                  <1> 	stosb
  1657 0001067A C3                  <1> 	retn
  1658                              <1> 
  1659                              <1> device_open:
  1660                              <1> 	; 08/10/2016 - TRDOS 386 (TRDOS v2.0)
  1661                              <1> 	; Complete device opening work for sysopen (device)
  1662                              <1> 	;
  1663                              <1> 	; INPUT -> 
  1664                              <1> 	;	EAX = Device Number (AL)
  1665                              <1> 	;        CL = Open mode (1 = read, 2 = write)
  1666                              <1> 	;	 CH = Device access byte (bit 0 = 0)		
  1667                              <1> 	; OUTPUT ->
  1668                              <1> 	;	EAX = Device Number	
  1669                              <1> 	;	CF = 0 -> device has been opened
  1670                              <1> 	;	CF = 1 -> device could not be opened
  1671                              <1> 	;
  1672                              <1> 	;  Modified registers: ebx, (edx, ecx, esi, edi, ebp)
  1673                              <1> 	;
  1674                              <1> 
  1675 0001067B 89C3                <1> 	mov	ebx, eax
  1676 0001067D 66C1E302            <1> 	shl	bx, 2 ; *4
  1677                              <1> 
  1678 00010681 F6C580              <1> 	test	ch, 80h ; bit 7, installable device driver flag
  1679 00010684 7406                <1> 	jz	short d_open_2 ; Kernel device
  1680                              <1> 	; installable device
  1681                              <1> d_open_1:
  1682 00010686 FFA3[B46B0100]      <1>         jmp	dword [ebx+IDEV_OADDR-4]
  1683                              <1> d_open_2:
  1684 0001068C FFA3[A41A0100]      <1> 	jmp	dword [ebx+KDEV_OADDR-4]
  1685                              <1> 
  1686                              <1> device_close:
  1687                              <1> 	; 08/10/2016 - TRDOS 386 (TRDOS v2.0)
  1688                              <1> 	; Complete device closing work for sysclose (device)
  1689                              <1> 	;
  1690                              <1> 	; INPUT -> 
  1691                              <1> 	;	EAX = Device Number (AL)
  1692                              <1> 	;        CL = Open mode (1 = read, 2 = write)
  1693                              <1> 	;	 CH = Device access byte (bit 0 = 0)		
  1694                              <1> 	; OUTPUT ->
  1695                              <1> 	;	EAX = Device Number	
  1696                              <1> 	;	CF = 0 -> device has been closed
  1697                              <1> 	;	CF = 1 -> device could not be closed
  1698                              <1> 	;
  1699                              <1> 	; Modified registers: ebx, (edx, ecx, esi, edi, ebp)
  1700                              <1> 	;
  1701                              <1> 
  1702 00010692 89C3                <1> 	mov	ebx, eax
  1703 00010694 66C1E302            <1> 	shl	bx, 2 ; *4
  1704                              <1> 
  1705 00010698 F6C580              <1> 	test	ch, 80h ; bit 7, installable device driver flag
  1706 0001069B 7406                <1> 	jz	short d_close_2 ; Kernel device
  1707                              <1> 	; installable device
  1708                              <1> d_close_1:
  1709 0001069D FFA3[D46B0100]      <1>         jmp	dword [ebx+IDEV_CADDR-4]
  1710                              <1> d_close_2:
  1711 000106A3 FFA3[F41A0100]      <1> 	jmp	dword [ebx+KDEV_CADDR-4]	
  1712                              <1> 
  1713                              <1> rnull:
  1714                              <1> 	; 07/10/2016 - TRDOS 386 (TRDOS v2.0)
  1715                              <1> 	; read null (read from null device)
  1716 000106A9 C3                  <1> 	retn
  1717                              <1> 
  1718                              <1> wnull:
  1719                              <1> 	; 07/10/2016 - TRDOS 386 (TRDOS v2.0)
  1720                              <1> 	; write null (write to null device)
  1721 000106AA C3                  <1> 	retn
  1722                              <1> 
  1723                              <1> dev_IRQ_service:
  1724                              <1> 	; 12/05/2017
  1725                              <1> 	; 13/04/2017
  1726                              <1> 	; 27/02/2017 - TRDOS 386 (TRDOS v2.0)
  1727                              <1> 	; INPUT ->
  1728                              <1> 	;	AL = IRQ Number (0 to 15)
  1729                              <1> 	;	
  1730 000106AB 53                  <1> 	push	ebx
  1731 000106AC 0FB6D8              <1> 	movzx	ebx, al
  1732 000106AF C0E302              <1> 	shl	bl, 2 ; * 4	
  1733 000106B2 8B9B[72700100]      <1> 	mov	ebx, [ebx+DEV_INT_HNDLR]
  1734 000106B8 21DB                <1> 	and 	ebx, ebx
  1735 000106BA 7404                <1>         jz	short dIRQ_s_retn
  1736 000106BC 50                  <1> 	push	eax
  1737                              <1> 
  1738 000106BD FFD3                <1> 	call	ebx
  1739                              <1> 
  1740 000106BF 58                  <1> 	pop	eax
  1741                              <1> dIRQ_s_retn:
  1742 000106C0 5B                  <1> 	pop	ebx
  1743 000106C1 C3                  <1> 	retn		
  1744                              <1> 
  1745                              <1> 
  1746                              <1> set_dev_IRQ_service:
  1747                              <1> 	; 13/04/2017 - TRDOS 386 (TRDOS v2.0)
  1748                              <1> 	;
  1749                              <1> 	; Set Device Interrupt Service
  1750                              <1> 	;
  1751                              <1> 	; INPUT ->
  1752                              <1> 	;	AL = IRQ Number
  1753                              <1> 	;	EBX = Hardware Interrupt Service Address
  1754                              <1> 	;
  1755                              <1> 	; Note: There is not a validation check here
  1756                              <1> 	;	because this procedure is called by
  1757                              <1> 	;	TRDOS 386 kernel !
  1758                              <1> 	;       (Even if a device driver does not exist
  1759                              <1> 	;	this setting may be used by sysaudio
  1760                              <1> 	;	and other system calls for hardware
  1761                              <1> 	;	components which use IRQ method for I/O.)
  1762                              <1> 	;
  1763                              <1> 	;push	esi
  1764 000106C2 0FB6F0              <1> 	movzx	esi, al
  1765 000106C5 66C1E602            <1> 	shl	si, 2 ; * 4	
  1766 000106C9 899E[72700100]      <1> 	mov	[esi+DEV_INT_HNDLR], ebx
  1767                              <1> 	;pop	esi
  1768 000106CF C3                  <1> 	retn		
  1769                              <1> 	
  1770                              <1> 
  1771                              <1> sysaudio: ; AUDIO FUNCTIONS
  1772                              <1> 	; 28/07/2020
  1773                              <1> 	; 27/07/2020
  1774                              <1> 	; 10/10/2017
  1775                              <1> 	; 22/06/2017
  1776                              <1> 	; 28/05/2017, 04/06/2017, 05/06/2017, 10/06/2017
  1777                              <1> 	; 01/05/2017, 12/05/2017, 15/05/2017, 20/05/2017
  1778                              <1> 	; 21/04/2017, 22/04/2017, 23/04/2017, 24/04/2017
  1779                              <1> 	; 10/04/2017, 13/04/2017, 14/04/2017, 16/04/2017
  1780                              <1> 	; 03/04/2017 (VIA VT8237R)
  1781                              <1> 	; 01/04/2016 (trdosk6.s -> tdosk8.s)
  1782                              <1> 	; 16/05/2016 - TRDOS 386 (TRDOS v2.0)
  1783                              <1> 	;
  1784                              <1> 	; Inputs:
  1785                              <1> 	;
  1786                              <1> 	;	BH = 0 -> Beep (PC Speaker)
  1787                              <1> 	;	     BL = Duration Counter (1 for 1/64 second)
  1788                              <1> 	;	     CX = Frequency Divisor (1193180/Frequency)
  1789                              <1> 	;		 (1331 for 886 Hz)
  1790                              <1> 	;
  1791                              <1> 	;	01/04/2017	
  1792                              <1> 	;
  1793                              <1> 	; 	BH = 1 -> DETECT (& ENABLE) AUDIO DEVICE
  1794                              <1> 	;	     BL = 0 : PC SPEAKER
  1795                              <1> 	;		  1 : SOUND BLASTER 16
  1796                              <1> 	;		  2 : INTEL AC'97
  1797                              <1> 	;		  3 : VIA VT8237R (VT8233)			 				
  1798                              <1> 	;		  4 : INTEL HDA
  1799                              <1> 	;	      5-FEh : unknown/invalid
  1800                              <1> 	;	        ; 04/06/2017
  1801                              <1> 	;		FFh : Get current audio device id
  1802                              <1> 	;
  1803                              <1> 	; 	BH = 2 -> ALLOCATE AUDIO BUFFER (for user)
  1804                              <1> 	;		ECX = Audio Buffer Size (must be equal to
  1805                              <1> 	;		      the half of DMA buffer size) 
  1806                              <1> 	;		EDX = Virtual Address of the buffer
  1807                              <1> 	;		      (This is not DMA buffer!)
  1808                              <1> 	;
  1809                              <1> 	;	BH = 3 -> INITIALIZE AUDIO DEVICE
  1810                              <1> 	;	     BL = 0,2 -> for Signal Response Byte	 	
  1811                              <1> 	;	     	CL = Signal Response Byte Value (fixed)
  1812                              <1> 	;				if BL = 0
  1813                              <1> 	;	             auto increment of S.R.B. value
  1814                              <1> 	;			 	if BL = 2
  1815                              <1> 	;	        EDX = Signal Response (Return) Byte Address
  1816                              <1> 	;	     	   			
  1817                              <1> 	;	     BL = 1 for CallBack Method	 	
  1818                              <1> 	;	    	EDX = CallBack Service Address (Virtual)
  1819                              <1> 	;
  1820                              <1> 	;	     BL > 2 -> invalid function	
  1821                              <1> 	;
  1822                              <1> 	;	    (Audio buffer must be allocated before
  1823                              <1> 	;	     initialization.) 		
  1824                              <1> 	;
  1825                              <1> 	;	BH = 4 -> START TO PLAY
  1826                              <1> 	;	     BL = Mode
  1827                              <1> 	;		  Bit 0 = mono/stereo (1 = stereo)		
  1828                              <1> 	;		  Bit 1 = 8 bit / 16 bit (1 = 16 bit)
  1829                              <1> 	;	     CX = Sampling Rate (Hz)
  1830                              <1> 	;
  1831                              <1> 	;	BH = 5 -> PAUSE
  1832                              <1> 	;	     BL = Any
  1833                              <1> 	;
  1834                              <1> 	;	BH = 6 -> CONTINUE TO PLAY
  1835                              <1> 	;	     BL = Any
  1836                              <1> 	;
  1837                              <1> 	;	BH = 7 -> STOP
  1838                              <1> 	;	     BL = Any
  1839                              <1> 	;
  1840                              <1> 	;	BH = 8 -> RESET 
  1841                              <1> 	;	     BL = Any
  1842                              <1> 	;
  1843                              <1> 	;	BH = 9 -> CANCEL (CALLBACK or S.R.B. SERVICE)
  1844                              <1> 	;	     BL = Any	
  1845                              <1> 	;	
  1846                              <1> 	;	BH = 10 -> DEALLOCATE AUDIO BUFFER (for user)
  1847                              <1> 	;	     BL = Any
  1848                              <1> 	;
  1849                              <1> 	;	BH = 11 -> SET VOLUME LEVEL
  1850                              <1> 	;	     BL: (Bit 0 to 6)
  1851                              <1> 	;		  0 = Master (Playback, Lineout) volume
  1852                              <1> 	;	     CL = Left Channel Volume
  1853                              <1> 	;	     CH = Right Channel Volume
  1854                              <1> 	;	
  1855                              <1> 	;	     Note: If BL >= 80h (Bit 7 of BL is set),
  1856                              <1> 	;	     volume level will be set for next playing
  1857                              <1> 	;	     (actual volume level will not be changed
  1858                              <1> 	;	     immediately)	
  1859                              <1> 	;
  1860                              <1> 	;	BH = 12 -> DISABLE AUDIO DEVICE
  1861                              <1> 	;	     (reset audio device and unlink dma buffer)	
  1862                              <1> 	;	     BL = Any	  		  	  	
  1863                              <1> 	;
  1864                              <1> 	;    	12/05/2017
  1865                              <1> 	;	BH = 13 -> MAP DMA BUFFER TO USER
  1866                              <1> 	;	    (for direct access to system's dma buffer)
  1867                              <1> 	;
  1868                              <1> 	;	     ECX = map size in bytes 
  1869                              <1> 	;		  (will be rounded up to page borders)
  1870                              <1> 	;	     EDX = Virtual Address of the buffer
  1871                              <1> 	;		  (Will be rounded up to page borders)
  1872                              <1> 	;
  1873                              <1> 	;	05/06/2017	
  1874                              <1> 	;    	04/06/2017
  1875                              <1> 	;	BH = 14 -> GET AUDIO DEVICE INFO
  1876                              <1> 	;	     BL: 0 = Audio Controller Info
  1877                              <1> 	;	       > 0 = Invalid for now! 
  1878                              <1> 	;
  1879                              <1> 	;	22/06/2017	
  1880                              <1> 	;	BH = 15 -> GET CURRENT SOUND DATA (for graphics)
  1881                              <1> 	;	     BL: 0 -> PCM OUT data
  1882                              <1> 	;	       > 0 -> Invalid for now! 
  1883                              <1> 	;	     ECX = 0 -> Get DMA Buffer Pointer
  1884                              <1> 	;		 EDX = Not Used
  1885                              <1> 	;	     ECX > 0 -> Byte count for buffer (EDX)	 	
  1886                              <1> 	;	         EDX = Buffer Address (Virtual)	
  1887                              <1> 	;
  1888                              <1> 	;	10/10/2017	
  1889                              <1> 	;	BH = 16 -> UPDATE DMA BUFFER DATA
  1890                              <1> 	;		   (by using the Audio Buffer content)
  1891                              <1> 	;	     BL = 0 : Update dma half buffer in sequence
  1892                              <1> 	;		      (automatic destination)	
  1893                              <1> 	;		  1 : Update 1st half of the dma buffer
  1894                              <1> 	;		  2 : Update 2nd half of the dma buffer
  1895                              <1> 	;		  3-FEh: Invalid!
  1896                              <1> 	;		  FFh = Get current flag value
  1897                              <1> 	;			(Half buffer number -1)
  1898                              <1> 	;
  1899                              <1> 	;
  1900                              <1> 	; Outputs:
  1901                              <1> 	;
  1902                              <1> 	;	For BH = 0 -> Beep
  1903                              <1> 	;	    None
  1904                              <1> 	;
  1905                              <1> 	;	01/04/2017
  1906                              <1> 	;
  1907                              <1> 	; 	For BH = 1 -> DETECT (& ENABLE) AUDIO DEVICE
  1908                              <1> 	;	    AH = 0 : PC SPEAKER
  1909                              <1> 	;		 1 : SOUND BLASTER 16
  1910                              <1> 	;		 2 : INTEL AC'97
  1911                              <1> 	;		 3 : VIA VT8237R (VT8233)			 				
  1912                              <1> 	;		 4 : INTEL HDA
  1913                              <1> 	;	      5-FFh : unknown/invalid
  1914                              <1> 	;	    AL = mode status
  1915                              <1> 	;		 bit 0 = mono /stereo (1 = stereo)
  1916                              <1> 	;		 bit 1 = 8 bit / 16 bit ( 1 = 16 bit)
  1917                              <1> 	;	    04/06/2017
  1918                              <1> 	;	    EBX = PCI DEVICE/VENDOR ID (if >0)
  1919                              <1> 	;		 (BX = VENDOR ID) 
  1920                              <1> 	;	    (if CF = 1 -> Error code in EAX)
  1921                              <1> 	;
  1922                              <1> 	; 	For BH = 2 -> ALLOCATE AUDIO BUFFER (for user)
  1923                              <1> 	;	    EAX = Physical Address of the buffer
  1924                              <1> 	;	    (if CF = 1 -> Error code in EAX)
  1925                              <1> 	;
  1926                              <1> 	;	For BH = 3 -> INITIALIZE AUDIO DEVICE
  1927                              <1> 	;	    (if CF = 1 -> Error code in EAX)
  1928                              <1> 	;
  1929                              <1> 	;	For BH = 4 -> START TO PLAY
  1930                              <1> 	;	    none (if CF = 1 -> Error code in EAX)	
  1931                              <1> 	;
  1932                              <1> 	;	For BH = 5 -> PAUSE
  1933                              <1> 	;	    none (if CF = 1 -> Error code in EAX)	
  1934                              <1> 	;
  1935                              <1> 	;	For BH = 6 -> CONTINUE TO PLAY
  1936                              <1> 	;	    none (if CF = 1 -> Error code in EAX)	
  1937                              <1> 	;
  1938                              <1> 	;	For BH = 7 -> STOP
  1939                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1940                              <1> 	;
  1941                              <1> 	;	For BH = 8 -> RESET 
  1942                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1943                              <1> 	;
  1944                              <1> 	;	For BH = 9 -> CANCEL (CALLBACK or S.R.B. SERVICE)
  1945                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1946                              <1> 	;	
  1947                              <1> 	;	For BH = 10 -> DEALLOCATE AUDIO BUFFER (for user)
  1948                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1949                              <1> 	;
  1950                              <1> 	;	For BH = 11 -> SET VOLUME LEVEL
  1951                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1952                              <1> 	;
  1953                              <1> 	;	For BH = 12 -> DISABLE AUDIO DEVICE
  1954                              <1> 	;	    none (if CF = 1 -> Error code in EAX)
  1955                              <1> 	; 
  1956                              <1> 	;    	12/05/2017
  1957                              <1> 	;	For BH = 13 -> MAP DMA BUFFER TO USER
  1958                              <1> 	;	    EAX = Physical Address of the buffer
  1959                              <1> 	;	    (if CF = 1 -> Error code in EAX)	
  1960                              <1> 	;
  1961                              <1> 	;    	04/06/2017
  1962                              <1> 	;	For BH = 14 -> GET AUDIO DEVICE INFO
  1963                              <1> 	;	(for BL = 0) ; 05/06/2017	
  1964                              <1> 	;	    EAX = IRQ Number in AL
  1965                              <1> 	;		  Audio Device Number in AH 
  1966                              <1> 	;	    EBX = DEV/VENDOR ID
  1967                              <1> 	;		 (DDDDDDDDDDDDDDDDVVVVVVVVVVVVVVVV)
  1968                              <1> 	;	    ECX = BUS/DEV/FN 
  1969                              <1> 	;		 (00000000BBBBBBBBDDDDDFFF00000000)
  1970                              <1> 	;	    EDX = NABMBAR/NAMBAR (for AC97)
  1971                              <1> 	;		  (Low word, DX = NAMBAR address)
  1972                              <1> 	;	    EDX = Base IO Addr (DX) for SB16 & VT8233	  			  		
  1973                              <1> 	;	    (if CF = 1 -> Error code in EAX)	
  1974                              <1> 	;	                 (ERR_DEV_NOT_RDY = 15)  
  1975                              <1> 	;
  1976                              <1> 	;	22/06/2017	
  1977                              <1> 	;	For BH = 15 -> GET CURRENT SOUND DATA
  1978                              <1> 	;			 (for graphics)
  1979                              <1> 	;	(for BL = 0)
  1980                              <1> 	;	 If ECX input is 0 
  1981                              <1> 	;	    EAX = DMA Buffer Current Position (Offset)
  1982                              <1> 	;	 If ECX input >  0
  1983                              <1> 	;	    EAX = Actual transfer count 		 	
  1984                              <1> 	;	    (Sound samples will be copied from 
  1985                              <1> 	;	     Current DMA Buffer Position to EDX
  1986                              <1> 	;	     virtual address as EAX bytes.)
  1987                              <1> 	;	 ((If CF = 1 ->  Error code in EAX))
  1988                              <1> 	;
  1989                              <1> 	;
  1990                              <1> 	;	10/10/2017	
  1991                              <1> 	;	For BH = 16 -> UPDATE DMA BUFFER DATA
  1992                              <1> 	;	    EAX = 0, if the updated (or current)
  1993                              <1> 	;		     half buffer is DMA half buffer 1
  1994                              <1> 	;	    EAX = 1, if the updated (or current)
  1995                              <1> 	; 		     half buffer is DMA half buffer 2 	  	
  1996                              <1> 	;	    (If CF = 1 -> Error code in EAX)	
  1997                              <1> 	;	
  1998                              <1> 
  1999 000106D0 80FF11              <1> 	cmp	bh, AUDIO1L/4
  2000 000106D3 0F83C1C8FFFF        <1> 	jnb	sysret
  2001                              <1> 
  2002 000106D9 C0E702              <1> 	shl	bh, 2 ; *4	
  2003 000106DC 0FB6F7              <1> 	movzx	esi, bh
  2004                              <1> 
  2005                              <1> 	; 22/04/2017
  2006 000106DF 31C0                <1> 	xor	eax, eax
  2007 000106E1 A3[64030300]        <1> 	mov	[u.r0], eax  ; 0
  2008                              <1> 		
  2009 000106E6 FF96[F1060100]      <1> 	call	dword [esi+AUDIO1]
  2010                              <1> 	;jc	error
  2011 000106EC E9A9C8FFFF          <1> 	jmp	sysret	
  2012                              <1> 
  2013 000106F1 [CC210000]          <1> AUDIO1:	dd	beep ; FUNCTION = 0 (bl = Duration Counter
  2014                              <1> 		     ; 		     cx = Frequency Divisor
  2015 000106F5 [35070100]          <1> 	dd	soundc_detect
  2016 000106F9 [D1070100]          <1> 	dd	sound_alloc
  2017 000106FD [8F080100]          <1> 	dd	soundc_init
  2018 00010701 [470A0100]          <1> 	dd	sound_play
  2019 00010705 [E30A0100]          <1> 	dd	sound_pause
  2020 00010709 [0D0B0100]          <1> 	dd	sound_continue
  2021 0001070D [370B0100]          <1> 	dd	sound_stop
  2022 00010711 [600B0100]          <1> 	dd	soundc_reset
  2023 00010715 [910B0100]          <1> 	dd	soundc_cancel
  2024 00010719 [B70B0100]          <1> 	dd	sound_dalloc
  2025 0001071D [E20B0100]          <1> 	dd	sound_volume
  2026 00010721 [340C0100]          <1> 	dd	soundc_disable
  2027 00010725 [A60C0100]          <1> 	dd	sound_dma_map
  2028 00010729 [150D0100]          <1> 	dd	soundc_info
  2029 0001072D [740D0100]          <1> 	dd	sound_data
  2030 00010731 [210E0100]          <1> 	dd	sound_update
  2031                              <1> 	
  2032                              <1> AUDIO1L	EQU	$ - AUDIO1
  2033                              <1> 
  2034                              <1> soundc_detect:
  2035                              <1> 	; FUNCTION = 1
  2036                              <1> 	; bl = Audio device type number 
  2037                              <1> 	; (0= pc speaker, 1 = sound blaster 16, 2 = intel ac97
  2038                              <1> 	;  3= via vt823x, 4 = intel HDA, 0FFh= any)
  2039                              <1> 	
  2040                              <1> 	; 04/06/2017
  2041 00010735 8A25[01710100]      <1> 	mov	ah, [audio_device]
  2042 0001073B 80FBFF              <1> 	cmp	bl, 0FFh ; get current audio device id
  2043 0001073E 7408                <1> 	je	short sysaudio0
  2044                              <1> 
  2045 00010740 20E4                <1> 	and	ah, ah
  2046 00010742 741E                <1> 	jz	short soundc_get_dev
  2047                              <1> 
  2048 00010744 38DC                <1> 	cmp	ah, bl
  2049 00010746 7567                <1> 	jne	short soundc_dev_err
  2050                              <1> 
  2051                              <1> sysaudio0:	
  2052 00010748 A0[02710100]        <1> 	mov	al, [audio_mode]
  2053                              <1> sysaudio1:
  2054 0001074D A3[64030300]        <1> 	mov	[u.r0], eax
  2055 00010752 8B1D[0C710100]      <1> 	mov	ebx, [audio_vendor] ; (DEVICE/VENDOR ID)
  2056 00010758 8B2D[60030300]      <1> 	mov	ebp, [u.usp]
  2057 0001075E 895D10              <1> 	mov	[ebp+16], ebx  ; ebx
  2058 00010761 C3                  <1> 	retn
  2059                              <1> 
  2060                              <1> soundc_get_dev:
  2061                              <1> 	; 28/05/2017
  2062                              <1> 	; 03/04/2017, 24/04/2017
  2063 00010762 C605[00710100]00    <1> 	mov	byte [audio_pci], 0
  2064 00010769 80FB03              <1> 	cmp	bl, 3 ; VIA VT8233 (VT8237R) Audio Controller & AC97 Codec
  2065                              <1> 	;jne	short soundc_get_dev_sb
  2066                              <1> 	; 28/05/2017
  2067 0001076C 7220                <1> 	jb	short soundc_get_dev_sb
  2068 0001076E 773F                <1> 	ja	short soundc_dev_err  ; temporary (28/05/2017)
  2069                              <1> 	;  		
  2070 00010770 E847180000          <1> 	call	DetectVT8233
  2071 00010775 7238                <1> 	jc	short soundc_dev_err
  2072                              <1> 	; eax = 0
  2073                              <1> 
  2074                              <1> 	;mov	ebx, [audio_vendor]
  2075                              <1> 	; ebx = DEVICE/VENDOR ID
  2076                              <1> 	;	DDDDDDDDDDDDDDDDVVVVVVVVVVVVVVVV
  2077                              <1> 
  2078 00010777 B003                <1> 	mov	al, 3  ; VIA VT8237R (VT3233) Audio Controller
  2079 00010779 88C4                <1> 	mov	ah, al
  2080                              <1> 
  2081                              <1> soundc_get_pci_dev_ok: ; 28/05/2017
  2082 0001077B FE05[00710100]      <1> 	inc	byte [audio_pci] ; = 1
  2083                              <1> soundc_get_dev_ok:
  2084                              <1> 	
  2085                              <1> soundc_get_dev_sb16_ok:
  2086 00010781 A2[01710100]        <1> 	mov	[audio_device], al
  2087 00010786 8825[02710100]      <1> 	mov	[audio_mode], ah ; stereo (bit0), 16 bit (bit1) capability	
  2088 0001078C EBBF                <1> 	jmp	short sysaudio1
  2089                              <1> 
  2090                              <1> soundc_get_dev_sb:
  2091                              <1> 	; 24/04/2017
  2092 0001078E 80FB01              <1> 	cmp	bl, 1 ; Sound Blaster 16
  2093 00010791 750E                <1> 	jne	short soundc_get_dev_ich ; 28/05/2017
  2094                              <1> 	;
  2095 00010793 E8481D0000          <1> 	call	DetectSB
  2096 00010798 7215                <1> 	jc	short soundc_dev_err
  2097 0001079A B801030000          <1> 	mov	eax, 0301h ; Sound Blaster 16
  2098 0001079F EBE0                <1> 	jmp	short soundc_get_dev_sb16_ok
  2099                              <1> 
  2100                              <1> soundc_get_dev_ich:
  2101                              <1> 	; 28/05/2017
  2102                              <1> 	;cmp	bl, 2 ; Intel AC'97 Audio Controller (ICH)
  2103                              <1> 	;jne	short soundc_dev_err ; Temporary  (28/05/2017)
  2104                              <1> 	;			     ; (Here will be modified just after
  2105                              <1> 	;			     ; new sound card code will be ready!)  	
  2106 000107A1 E809180000          <1> 	call	DetectICH
  2107 000107A6 7207                <1> 	jc	short soundc_dev_err
  2108                              <1> 	;
  2109 000107A8 B802030000          <1> 	mov	eax, 0302h ; AC'97 (ICH)
  2110 000107AD EBCC                <1> 	jmp	short soundc_get_pci_dev_ok
  2111                              <1> 
  2112                              <1> soundc_dev_err:
  2113 000107AF B80F000000          <1> 	mov	eax, ERR_DEV_NOT_RDY ; Device not ready !
  2114 000107B4 EB0C                <1> 	jmp	short sysaudio_err
  2115                              <1> 
  2116                              <1> sound_buff_error:
  2117 000107B6 B82E000000          <1> 	mov	eax, ERR_BUFFER ; Buffer error !
  2118 000107BB EB05                <1> 	jmp	short sysaudio_err
  2119                              <1> 
  2120                              <1> soundc_respond_err:
  2121                              <1> 	; ERR_TIME_OUT ; 'time out !' error	
  2122 000107BD B819000000          <1> 	mov	eax, ERR_DEV_NOT_RESP ; 'device not responding !' error
  2123                              <1> sysaudio_err:
  2124 000107C2 A3[64030300]        <1> 	mov	[u.r0], eax
  2125 000107C7 A3[C8030300]        <1> 	mov	[u.error], eax
  2126 000107CC E9A9C7FFFF          <1> 	jmp	error
  2127                              <1> 
  2128                              <1> sound_alloc:
  2129                              <1> 	; FUNCTION =  2
  2130                              <1> 	; ecx = audio buffer size (in bytes)
  2131                              <1> 	; edx = audio buffer address (virtual)
  2132                              <1> 	; 27/07/2020
  2133                              <1> 	; 28/05/2017
  2134                              <1> 	; 01/05/2017, 15/05/2017
  2135                              <1> 	; 21/04/2017, 24/04/2017
  2136 000107D1 803D[00710100]00    <1> 	cmp	byte [audio_pci], 0
  2137 000107D8 7708                <1> 	ja	short snd_alloc_0
  2138                              <1> 	; Max. 64KB DMA buffer !!!
  2139 000107DA 81F900800000        <1> 	cmp	ecx, 32768
  2140 000107E0 77D4                <1> 	ja	short sound_buff_error
  2141                              <1> snd_alloc_0:
  2142                              <1> 	; 15/05/2017
  2143 000107E2 81F900100000        <1> 	cmp	ecx, 4096 ; PAGE_SIZE
  2144 000107E8 72CC                <1> 	jb	short sound_buff_error
  2145                              <1> 	;
  2146 000107EA A1[14710100]        <1> 	mov	eax, [audio_buffer] ; audio buffer address (current)
  2147 000107EF 09C0                <1> 	or	eax, eax
  2148 000107F1 7445                <1> 	jz	short snd_alloc_2
  2149                              <1> 	; audio buffer exists !
  2150 000107F3 8A1D[B3030300]      <1> 	mov	bl, [u.uno]
  2151 000107F9 3A1D[29710100]      <1> 	cmp	bl, [audio_user]
  2152 000107FF 0F85FC000000        <1> 	jne	sndc_owner_error ; not owner !
  2153 00010805 39D0                <1> 	cmp	eax, edx ; same virtual buffer address ?
  2154 00010807 7508                <1> 	jne	short snd_alloc_1
  2155 00010809 3B0D[1C710100]      <1> 	cmp	ecx, [audio_buff_size]
  2156 0001080F 746C                <1> 	je	short snd_alloc_3 ; Nothing to do !
  2157                              <1> 				  ; Buffer has been set already!
  2158                              <1> snd_alloc_1:
  2159 00010811 51                  <1> 	push	ecx
  2160 00010812 52                  <1> 	push	edx
  2161 00010813 89C3                <1> 	mov	ebx, eax ; audio buffer address (current)
  2162 00010815 8B0D[1C710100]      <1> 	mov	ecx, [audio_buff_size]
  2163 0001081B E8CA56FFFF          <1> 	call	deallocate_user_pages
  2164 00010820 5A                  <1> 	pop	edx
  2165 00010821 59                  <1> 	pop	ecx
  2166 00010822 31C0                <1> 	xor	eax, eax ; 0
  2167 00010824 A3[14710100]        <1> 	mov	[audio_buffer], eax  ; 0
  2168 00010829 A3[18710100]        <1>  	mov	[audio_p_buffer], eax  ; 0
  2169 0001082E A3[1C710100]        <1>  	mov	[audio_buff_size], eax
  2170 00010833 A2[29710100]        <1> 	mov	[audio_user], al ; 0
  2171                              <1> snd_alloc_2:
  2172 00010838 89D3                <1> 	mov	ebx, edx
  2173                              <1> 	; 01/05/2017
  2174 0001083A BA00F0FFFF          <1> 	mov	edx, ~PAGE_OFF ; truncating page offsets
  2175                              <1> 			       ; for aligning to page borders	
  2176                              <1> 	;and	eax, edx
  2177 0001083F 21D3                <1> 	and	ebx, edx
  2178 00010841 21D1                <1> 	and	ecx, edx
  2179                              <1> 	; 15/05/2017
  2180                              <1> 	; EAX = Beginning address (physical)
  2181                              <1> 	; EAX = 0 -> Allocate mem block from the 1st proper aperture	
  2182                              <1> 	; ECX = Number of bytes to be allocated		
  2183 00010843 E84753FFFF          <1> 	call	allocate_memory_block
  2184 00010848 0F8268FFFFFF        <1> 	jc	sound_buff_error
  2185                              <1> 	; EAX = Physical address of the allocated memory block
  2186                              <1> 	; ECX = Allocated bytes (as truncated to page border)
  2187                              <1> 	; EBX = Virtual address (as truncated to page border)
  2188 0001084E 50                  <1> 	push	eax
  2189 0001084F 53                  <1> 	push	ebx
  2190 00010850 51                  <1> 	push	ecx
  2191 00010851 E88957FFFF          <1> 	call	allocate_user_pages
  2192 00010856 59                  <1> 	pop	ecx
  2193 00010857 5B                  <1> 	pop	ebx
  2194 00010858 58                  <1> 	pop	eax
  2195 00010859 722A                <1> 	jc	short snd_alloc_4  ; insufficient memory, buff error
  2196                              <1> 	; eax = physical address of the user's audio buffer
  2197                              <1> 	; ebx = virtual address of the user's audio buffer
  2198                              <1> 	; ecx = buffer size (in bytes)
  2199 0001085B A3[18710100]        <1> 	mov	[audio_p_buffer], eax
  2200 00010860 891D[14710100]      <1> 	mov	[audio_buffer], ebx
  2201 00010866 890D[1C710100]      <1>  	mov	[audio_buff_size], ecx
  2202 0001086C 8A15[B3030300]      <1> 	mov	dl, [u.uno]
  2203 00010872 8815[29710100]      <1> 	mov	[audio_user], dl
  2204 00010878 A3[64030300]        <1> 	mov	[u.r0], eax
  2205                              <1> snd_alloc_3:
  2206                              <1> 	; 27/07/2020
  2207 0001087D C605[28710100]00    <1> 	mov	byte [audio_flag], 0 ; clear dma half buffer flag
  2208                              <1> 	;	
  2209 00010884 C3                  <1> 	retn
  2210                              <1> snd_alloc_4:
  2211                              <1> 	; 15/05/2017
  2212                              <1> 	; EAX = Beginning address (physical)
  2213                              <1> 	; ECX = Number of bytes to be deallocated
  2214 00010885 E81255FFFF          <1> 	call	deallocate_memory_block
  2215 0001088A E927FFFFFF          <1> 	jmp	sound_buff_error  ; insufficient memory, buff error
  2216                              <1> 
  2217                              <1> soundc_init:
  2218                              <1> 	; FUNCTION = 3 
  2219                              <1> 	; bl = method (0= s.r.b., 1= callback, 2= auto incr s.r.b.)
  2220                              <1> 	; cl = signal response byte (initial or fixed) value
  2221                              <1> 	; edx = signal response byte or callback address
  2222                              <1> 	; 27/07/2020
  2223                              <1> 	; 28/05/2017
  2224                              <1> 	; 12/05/2017, 20/05/2017
  2225                              <1> 	; 22/04/2017, 23/04/2017, 24/04/2017
  2226                              <1> 	; 13/04/2017, 14/04/2017, 16/04/2017, 21/04/2017
  2227                              <1> 	; 03/04/2017, 10/04/2017
  2228                              <1> 
  2229 0001088F A0[01710100]        <1> 	mov	al, [audio_device]
  2230 00010894 20C0                <1> 	and	al, al
  2231 00010896 7549                <1> 	jnz	short sndc_init_6
  2232                              <1> 	;
  2233 00010898 C605[00710100]00    <1> 	mov	byte [audio_pci], 0
  2234 0001089F 52                  <1> 	push	edx
  2235 000108A0 53                  <1> 	push	ebx
  2236 000108A1 51                  <1> 	push	ecx
  2237 000108A2 E8391C0000          <1> 	call	DetectSB
  2238 000108A7 7213                <1> 	jc	short sndc_init_8
  2239 000108A9 66B80103            <1> 	mov	ax, 0301h ; Sound Blaster 16
  2240 000108AD EB1E                <1> 	jmp	short sndc_init_7
  2241                              <1> 
  2242                              <1> sndc_init_11:
  2243                              <1> 	; 28/05/2017
  2244 000108AF E8FB160000          <1> 	call	DetectICH ; Detect AC'97 (ICH) Audio Controller
  2245 000108B4 7217                <1> 	jc	short sndc_init_7
  2246 000108B6 66B80203            <1> 	mov	ax, 0302h ; Intel AC'97 Audio Device
  2247 000108BA EB0B                <1> 	jmp	short sndc_init_12 ; (PCI device)
  2248                              <1> 
  2249                              <1> sndc_init_8:
  2250 000108BC E8FB160000          <1> 	call	DetectVT8233
  2251                              <1> 	;jc	short sndc_init_7
  2252 000108C1 72EC                <1> 	jc	sndc_init_11 ; 28/05/2017
  2253                              <1> 	; eax = 0
  2254 000108C3 B003                <1> 	mov	al, 3	; VIA VT8237R (VT3233) Audio Controller
  2255 000108C5 88C4                <1> 	mov	ah, al
  2256                              <1> 
  2257                              <1> sndc_init_12:
  2258 000108C7 FE05[00710100]      <1> 	inc	byte [audio_pci] ; = 1
  2259                              <1> sndc_init_7:
  2260 000108CD 59                  <1> 	pop	ecx
  2261 000108CE 5B                  <1> 	pop	ebx
  2262 000108CF 5A                  <1> 	pop	edx
  2263 000108D0 0F82D9FEFFFF        <1> 	jc	soundc_dev_err
  2264                              <1> 	;
  2265 000108D6 A2[01710100]        <1> 	mov	[audio_device], al
  2266 000108DB 8825[02710100]      <1> 	mov	[audio_mode], ah ; stereo (bit0), 16 bit (bit1) capability
  2267                              <1> 
  2268                              <1> sndc_init_6:
  2269 000108E1 833D[14710100]00    <1> 	cmp	dword [audio_buffer], 0
  2270 000108E8 0F86C8FEFFFF        <1> 	jna	sound_buff_error
  2271                              <1> 
  2272 000108EE A0[B3030300]        <1> 	mov	al, [u.uno]
  2273 000108F3 8A25[29710100]      <1> 	mov	ah, [audio_user]
  2274 000108F9 08E4                <1> 	or	ah, ah
  2275 000108FB 7418                <1> 	jz	short sndc_init0
  2276 000108FD 38E0                <1> 	cmp	al, ah
  2277 000108FF 7419                <1> 	je	short sndc_init1
  2278                              <1> 
  2279                              <1> sndc_owner_error:
  2280 00010901 B80B000000          <1> 	mov	eax, ERR_NOT_OWNER ; 'permission denied !' error
  2281                              <1> sndc_perm_error:
  2282 00010906 A3[64030300]        <1> 	mov	[u.r0], eax
  2283 0001090B A3[C8030300]        <1> 	mov	[u.error], eax
  2284 00010910 E965C6FFFF          <1> 	jmp	error
  2285                              <1> sndc_init0:
  2286 00010915 A2[29710100]        <1> 	mov	[audio_user], al
  2287                              <1> sndc_init1:
  2288 0001091A 8915[2C710100]      <1> 	mov	[audio_cb_addr], edx
  2289 00010920 881D[2A710100]      <1> 	mov	[audio_cb_mode], bl
  2290 00010926 880D[2B710100]      <1> 	mov	[audio_srb], cl
  2291                              <1> 
  2292                              <1> 	; 27/07/2020
  2293                              <1> 	;mov	byte [audio_flag], 0  ; clear dma half buffer flag
  2294                              <1> 
  2295                              <1> 	; 24/04/2017
  2296 0001092C 803D[01710100]03    <1> 	cmp	byte [audio_device], 3 ; VT8233 (VT8237R)
  2297 00010933 7438                <1> 	je	short sndc_init_9
  2298                              <1> 	;ja	short soundc_respond_err ; temporary (28/05/2017)
  2299 00010935 803D[01710100]01    <1> 	cmp	byte [audio_device], 1 ; SB 16
  2300 0001093C 7510                <1> 	jne	short sndc_init_13
  2301 0001093E BB[05270100]        <1> 	mov	ebx, sb16_int_handler
  2302                              <1> 	; Note: 'SbInit' is at 'Start to Play' stage
  2303                              <1> 	; 20/05/2017
  2304 00010943 66C705[36710100]08- <1> 	mov	word [audio_master_volume], 0808h ; 2/8
  2304 0001094B 08                  <1>
  2305 0001094C EB3F                <1> 	jmp	short sndc_init_10
  2306                              <1> sndc_init_13:
  2307                              <1> 	; 28/05/2017
  2308 0001094E 803D[01710100]02    <1> 	cmp	byte [audio_device], 2 ; AC 97 (ICH)	
  2309 00010955 0F8562FEFFFF        <1> 	jne	soundc_respond_err ; temporary (28/05/2017)
  2310                              <1> 
  2311 0001095B E8FA1E0000          <1> 	call	ac97_codec_config
  2312 00010960 0F8257FEFFFF        <1> 	jc	soundc_respond_err ; codec error !
  2313                              <1> 
  2314 00010966 BB[412A0100]        <1> 	mov	ebx, ac97_int_handler
  2315 0001096B EB20                <1> 	jmp	short sndc_init_10	
  2316                              <1> 
  2317                              <1> sndc_init_9:
  2318                              <1> 	;call	reset_codec
  2319                              <1> 	;; eax = 1
  2320                              <1> 	;call	codec_io_w16 ; w32
  2321 0001096D E8C1170000          <1> 	call	init_codec ; 28/05/2017
  2322 00010972 0F8245FEFFFF        <1> 	jc	soundc_respond_err ; codec error !
  2323                              <1> 
  2324 00010978 E8E8190000          <1> 	call	channel_reset
  2325                              <1> 
  2326                              <1> 	; setup the Codec (actually mixer registers) 
  2327 0001097D E808190000          <1>         call    codec_config  ; unmute codec, set rates.
  2328 00010982 0F8235FEFFFF        <1> 	jc	soundc_respond_err ; codec error !
  2329                              <1> 
  2330 00010988 BB[F7220100]        <1> 	mov	ebx, vt8233_int_handler
  2331                              <1> sndc_init_10:
  2332                              <1> 	; 13/04/2017
  2333 0001098D A0[03710100]        <1> 	mov	al, [audio_intr] ; IRQ number	
  2334 00010992 E82BFDFFFF          <1> 	call	set_dev_IRQ_service
  2335                              <1> 
  2336                              <1> 	; SETUP (audio) INTERRUPT CALLBACK SERVICE
  2337 00010997 8A1D[03710100]      <1> 	mov	bl, [audio_intr] ; IRQ number
  2338 0001099D 8A3D[2A710100]      <1> 	mov	bh, [audio_cb_mode]
  2339 000109A3 FEC7                <1> 	inc	bh  ; 1 = Signal Response Byte method (fixed value)
  2340                              <1> 		    ; 2 = Callback service method
  2341                              <1> 		    ; 3 = Auto Increment S.R.B. method 	
  2342 000109A5 8A0D[2B710100]      <1> 	mov	cl, [audio_srb]
  2343 000109AB 8B15[2C710100]      <1> 	mov	edx, [audio_cb_addr]
  2344 000109B1 A0[29710100]        <1> 	mov	al, [audio_user]
  2345                              <1> 	; 14/04/2017
  2346 000109B6 E8E1040000          <1>  	call	set_irq_callback_service
  2347                              <1> 	; 16/04/2017
  2348 000109BB A3[64030300]        <1> 	mov	[u.r0], eax
  2349                              <1> 	;jnc	sysret
  2350 000109C0 7316                <1> 	jnc	short sndc_init2 ; 21/04/2017
  2351                              <1> 	;
  2352 000109C2 A3[C8030300]        <1> 	mov	dword [u.error], eax
  2353                              <1> 
  2354 000109C7 A0[03710100]        <1> 	mov	al, [audio_intr] ; IRQ number	
  2355 000109CC 31DB                <1> 	xor	ebx, ebx ; reset IRQ handler address
  2356 000109CE E8EFFCFFFF          <1> 	call	set_dev_IRQ_service
  2357                              <1> 
  2358 000109D3 E9A2C5FFFF          <1> 	jmp	error
  2359                              <1> 
  2360                              <1> sndc_init2:
  2361                              <1> 	; 21/04/2017
  2362 000109D8 8B0D[1C710100]      <1> 	mov	ecx, [audio_buff_size] ; audio buffer size
  2363 000109DE D1E1                <1> 	shl	ecx, 1 ; *2
  2364 000109E0 A1[20710100]        <1> 	mov	eax, [audio_dma_buff]
  2365 000109E5 21C0                <1> 	and	eax, eax
  2366 000109E7 7415                <1> 	jz	short sndc_init3
  2367                              <1> 
  2368 000109E9 8B15[24710100]      <1> 	mov	edx, [audio_dmabuff_size] ; dma buffer size
  2369 000109EF 39D1                <1> 	cmp	ecx, edx
  2370 000109F1 744D                <1> 	je	short sndc_init5
  2371                              <1> 
  2372 000109F3 87CA                <1> 	xchg	ecx, edx
  2373 000109F5 E8A253FFFF          <1> 	call	deallocate_memory_block
  2374 000109FA 87D1                <1> 	xchg	edx, ecx
  2375 000109FC 31C0                <1> 	xor	eax, eax
  2376                              <1> sndc_init3:
  2377                              <1> 	; 12/05/2017
  2378 000109FE 803D[01710100]01    <1> 	cmp	byte [audio_device], 1 ; SB 16
  2379 00010A05 7515                <1> 	jne	short sndc_init4
  2380 00010A07 C705[20710100]-     <1> 	mov	dword [audio_dma_buff], sb16_dma_buffer
  2380 00010A0D [00000200]          <1>
  2381 00010A11 C705[24710100]0000- <1> 	mov	dword [audio_dmabuff_size], 65536
  2381 00010A19 0100                <1>
  2382                              <1> 	;xor	eax, eax
  2383                              <1> 	;mov	[u.r0], eax ; 0 = no error, successful
  2384 00010A1B C3                  <1> 	retn 
  2385                              <1> 
  2386                              <1> sndc_init4:
  2387                              <1> 	; EAX = Beginning address (physical)
  2388                              <1> 	; EAX = 0 -> Allocate mem block from the 1st proper aperture	
  2389                              <1> 	; ECX = Number of bytes to be allocated	(>0)	
  2390 00010A1C E86E51FFFF          <1> 	call	allocate_memory_block
  2391 00010A21 0F828FFDFFFF        <1> 	jc	sound_buff_error
  2392                              <1> 
  2393                              <1> 	; set dma buffer address and size parameters
  2394 00010A27 A3[20710100]        <1> 	mov	[audio_dma_buff], eax ; dma buffer address
  2395 00010A2C 890D[24710100]      <1> 	mov	[audio_dmabuff_size], ecx ; dma buffer size
  2396                              <1> ;	; EAX = Beginning (physical) addr of the allocated mem block
  2397                              <1> ;	; ECX = Num of allocated bytes (rounded up to page borders)
  2398                              <1> ;	cmp	byte [audio_pci], 0 ; AC97 audio controller ?
  2399                              <1> ;	ja	short sndc_init4
  2400                              <1> ;
  2401                              <1> ;	; Sound Blaster 16 uses classic DMA
  2402                              <1> ;	mov	edx, eax
  2403                              <1> ;	add	edx, ecx
  2404                              <1> ;	cmp	edx, 1000000h ; 1st 16 MB
  2405                              <1> ;	jna	short sndc_init4
  2406                              <1> ;
  2407                              <1> ;	; error !
  2408                              <1> ;	; restore Memory Allocation Table Content
  2409                              <1> ;	; EAX = Beginning address (physical)
  2410                              <1> ;	; ECX = Number of bytes to be deallocated
  2411                              <1> ;	call	deallocate_memory_block
  2412                              <1> ;	; reset dma buffer address and size parameters
  2413                              <1> ;	xor	eax, eax ; 0
  2414                              <1> ;	mov	[audio_dma_buff], eax ; 0
  2415                              <1> ;	mov	[audio_dmabuff_size], ecx ; 0
  2416                              <1> ;	jmp	sound_buff_error				
  2417                              <1> ;
  2418                              <1> ;sndc_init4:
  2419 00010A32 803D[01710100]03    <1> 	cmp	byte [audio_device], 3
  2420                              <1> 	;jne	short sndc_init5
  2421 00010A39 7506                <1> 	jne	short sndc_init14 ; 28/05/2017
  2422 00010A3B E866190000          <1> 	call	set_vt8233_bdl	
  2423                              <1> sndc_init5:
  2424                              <1> 	;sub	eax, eax ; 0
  2425                              <1> 	;mov	[u.r0], eax ; 0 = no error, successful
  2426 00010A40 C3                  <1> 	retn
  2427                              <1> sndc_init14:
  2428 00010A41 E82D1F0000          <1> 	call	set_ac97_bdl
  2429                              <1> 	;jmp	short sndc_init5
  2430 00010A46 C3                  <1> 	retn
  2431                              <1> 
  2432                              <1> sound_play:
  2433                              <1> 	; FUNCTION = 4 
  2434                              <1> 	; bl = Mode 
  2435                              <1> 	;      bit 0 = mono/stereo (1 = stereo)		
  2436                              <1> 	;      bit 1 = 8 bit / 16 bit (1 = 16 bit)
  2437                              <1> 	; cx = Sampling Rate (Hz)
  2438                              <1> 
  2439                              <1> 	; 13/06/2017
  2440                              <1> 	; Note: Even if Mode bits are not 11b,
  2441                              <1> 	; 	AC'97 Audio Controller (&Codec)
  2442                              <1> 	;	will play audio samples as 16 bit, stereo
  2443                              <1> 	;	samples.
  2444                              <1> 	;	(Program must fill the audio buffer
  2445                              <1> 	;	as required; 8 bit samples must be converted
  2446                              <1> 	;	to 16 bit samples and mono samples must be
  2447                              <1> 	;	converted to stereo samples...)
  2448                              <1> 	; 
  2449                              <1> 	; 28/07/2020
  2450                              <1> 	; 27/07/2020	 	
  2451                              <1> 	; 28/05/2017
  2452                              <1> 	; 15/05/2017, 20/05/2017
  2453                              <1> 	; 21/04/2017, 24/04/2017
  2454                              <1> 	; ... device check at first
  2455 00010A47 A0[01710100]        <1> 	mov	al, [audio_device]
  2456 00010A4C 08C0                <1> 	or	al, al ; 0 ; pc speaker or invalid 
  2457 00010A4E 0F847217FFFF        <1> 	jz	beeper_gfx ; 'video.s' ; temporary !
  2458                              <1> ;	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2459                              <1> ;	je	short snd_play_1
  2460                              <1> ;	cmp	al, 1 ; SB 16
  2461                              <1> ;	jne	soundc_dev_err ; temporary !
  2462                              <1> ;snd_play_0:
  2463                              <1> 	; ... buffer & (buffer) owner check at second
  2464 00010A54 833D[14710100]00    <1> 	cmp	dword [audio_buffer], 0
  2465 00010A5B 0F8655FDFFFF        <1> 	jna	sound_buff_error
  2466 00010A61 A0[B3030300]        <1> 	mov	al, [u.uno]
  2467 00010A66 3A05[29710100]      <1> 	cmp	al, [audio_user]
  2468 00010A6C 0F858FFEFFFF        <1> 	jne	sndc_owner_error
  2469                              <1> 
  2470 00010A72 66890D[32710100]    <1> 	mov	[audio_freq], cx ; sample frequency (Hertz)
  2471 00010A79 88D8                <1> 	mov	al, bl
  2472 00010A7B 2401                <1> 	and	al, 1 ; mono/stereo (1= stereo)
  2473 00010A7D FEC0                <1> 	inc	al ; channels
  2474 00010A7F A2[31710100]        <1> 	mov	[audio_stmo], al ; sound channels (1 or 2)
  2475 00010A84 B008                <1> 	mov	al, 8
  2476 00010A86 F6C302              <1> 	test	bl, 2 ; bits per sample (1= 16 bit)
  2477 00010A89 7402                <1> 	jz	short snd_play_bps
  2478 00010A8B D0E0                <1> 	shl	al, 1  
  2479                              <1> snd_play_bps:	
  2480 00010A8D A2[30710100]        <1> 	mov	[audio_bps], al
  2481                              <1> 
  2482                              <1> 	; Transfer ring 3 (user's) audio buffer content to dma buffer
  2483 00010A92 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff] ; dma buffer (ring 0)
  2484 00010A98 09FF                <1> 	or	edi, edi
  2485 00010A9A 0F8416FDFFFF        <1> 	jz	sound_buff_error
  2486                              <1> 
  2487                              <1> 	; 27/07/2020
  2488                              <1> 
  2489 00010AA0 8B35[18710100]      <1> 	mov	esi, [audio_p_buffer] ; physical address (ring 3)
  2490                              <1> 	;mov	ecx, [audio_buff_size] ; 15/05/2017
  2491 00010AA6 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size] ; 27/07/2020
  2492                              <1> 	;or	ecx, ecx 
  2493                              <1> 	;jz	sound_buff_error
  2494                              <1> 	; 28/07/2020
  2495 00010AAC D1E9                <1> 	shr	ecx, 1  ; dma half buffer size
  2496                              <1> 
  2497 00010AAE 8035[28710100]01    <1> 	xor	byte [audio_flag], 1 ;  0 -> 1, 1 -> 0
  2498 00010AB5 7502                <1> 	jnz	short snd_play_0 ; [audio_flag] = 1
  2499                              <1> 				 ; fill dma half buffer 1
  2500                              <1> 	; [audio_flag] = 0
  2501                              <1> 	
  2502                              <1> 	; fill dma half buffer 2
  2503 00010AB7 01CF                <1> 	add	edi, ecx
  2504                              <1> 
  2505                              <1> snd_play_0:
  2506                              <1> 	;rep	movsb
  2507 00010AB9 C1E902              <1> 	shr	ecx, 2  ; convert byte count to dword count
  2508 00010ABC F3A5                <1> 	rep	movsd
  2509                              <1> 
  2510                              <1> 	; here, if [audio_flag] = 0, interrupt handler will update
  2511                              <1> 				; dma half buffer 2 
  2512                              <1> 				; (user's audio buffer data will be 
  2513                              <1> 				; copied into dma half buffer 2) 
  2514                              <1> 	;; 20/05/2017
  2515                              <1> 	;mov	byte [audio_flag], 1 ; next half (on next time)
  2516                              <1> 
  2517                              <1> 	; 24/04/2017
  2518 00010ABE A0[01710100]        <1> 	mov	al, [audio_device]
  2519 00010AC3 3C03                <1> 	cmp	al, 3 ; VT8233 (VT8237R) 
  2520 00010AC5 7410                <1> 	je	short snd_play_1
  2521 00010AC7 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2522 00010AC9 7512                <1> 	jne	short snd_play_2  ; 28/05/2017
  2523 00010ACB E8DE1A0000          <1> 	call	SbInit_play
  2524 00010AD0 0F82E7FCFFFF        <1> 	jc	soundc_respond_err
  2525 00010AD6 C3                  <1> 	retn
  2526                              <1> 
  2527                              <1> snd_play_1:	
  2528 00010AD7 E801190000          <1> 	call	vt8233_start_play
  2529 00010ADC C3                  <1> 	retn
  2530                              <1> 
  2531                              <1> snd_play_2:
  2532                              <1> 	; 28/05/2017
  2533                              <1> 	;cmp	al, 2 ; AC'97
  2534                              <1> 	;jne	short snd_play_3
  2535                              <1> 
  2536 00010ADD E8C51E0000          <1> 	call	ac97_start_play
  2537 00010AE2 C3                  <1> 	retn
  2538                              <1> 
  2539                              <1> ;snd_play_3:
  2540                              <1> ;	;call	hda_start_play
  2541                              <1> ;	retn
  2542                              <1> 
  2543                              <1> sound_pause:
  2544                              <1> 	; FUNCTION = 5
  2545                              <1> 	; Pause
  2546                              <1> 	; 28/05/2017
  2547                              <1> 	; 24/04/2017
  2548                              <1> 	; 22/04/2017
  2549 00010AE3 E814030000          <1> 	call	snd_dev_check
  2550 00010AE8 7275                <1> 	jc	short snd_nothing ; temporary.
  2551 00010AEA E81A030000          <1> 	call	snd_buf_check
  2552 00010AEF 726E                <1> 	jc	short snd_nothing ; temporary.
  2553 00010AF1 A0[01710100]        <1> 	mov	al, [audio_device]
  2554 00010AF6 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2555 00010AF8 7409                <1> 	je	short snd_pause_1
  2556 00010AFA 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2557 00010AFC 750A                <1> 	jne	short snd_pause_2 ; 28/05/2017
  2558 00010AFE E9891C0000          <1> 	jmp	sb16_pause
  2559                              <1> snd_pause_1:
  2560 00010B03 E98E190000          <1> 	jmp	vt8233_pause
  2561                              <1> snd_pause_2:
  2562                              <1> 	; 28/05/2017
  2563                              <1> 	;cmp	al, 2 ; AC'97
  2564                              <1> 	;jne	short snd_nothing ; temporary.
  2565 00010B08 E928200000          <1> 	jmp	ac97_pause
  2566                              <1> 
  2567                              <1> sound_continue:
  2568                              <1> 	; FUNCTION = 6
  2569                              <1> 	; Continue to play
  2570                              <1> 	; 28/05/2017
  2571                              <1> 	; 22/04/2017
  2572 00010B0D E8EA020000          <1> 	call	snd_dev_check
  2573 00010B12 724B                <1> 	jc	short snd_nothing ; temporary.
  2574 00010B14 E8F0020000          <1> 	call	snd_buf_check
  2575 00010B19 7244                <1> 	jc	short snd_nothing ; temporary.
  2576 00010B1B A0[01710100]        <1> 	mov	al, [audio_device]
  2577 00010B20 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2578 00010B22 7409                <1> 	je	short snd_cont_1
  2579 00010B24 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2580 00010B26 750A                <1> 	jne	short snd_cont_2 ; 28/05/2017
  2581 00010B28 E9821C0000          <1> 	jmp	sb16_continue
  2582                              <1> snd_cont_1:
  2583 00010B2D E915190000          <1> 	jmp	vt8233_play
  2584                              <1> snd_cont_2:
  2585                              <1> 	; 28/05/2017
  2586                              <1> 	;cmp	al, 2 ; AC'97
  2587                              <1> 	;jne	short snd_nothing ; temporary.
  2588 00010B32 E9C61E0000          <1> 	jmp	ac97_play
  2589                              <1> 
  2590                              <1> sound_stop:
  2591                              <1> 	; FUNCTION = 7
  2592                              <1> 	; Stop playing
  2593                              <1> 	; 28/05/2017
  2594                              <1> 	; 24/05/2017
  2595                              <1> 	; 21/04/2017, 22/04/2017, 24/04/2017
  2596 00010B37 E8C0020000          <1> 	call	snd_dev_check
  2597 00010B3C 7221                <1> 	jc	short snd_nothing ; temporary.
  2598                              <1> 	;call	snd_buf_check
  2599 00010B3E E8CF020000          <1> 	call	snd_user_check ; 24/05/2017
  2600 00010B43 721A                <1> 	jc	short snd_nothing ; temporary.	
  2601                              <1> 	
  2602 00010B45 A0[01710100]        <1> 	mov	al, [audio_device]
  2603 00010B4A 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2604 00010B4C 0F844B180000        <1> 	je	vt8233_stop
  2605                              <1> 	; 28/05/2017
  2606                              <1> 	;ja	short snd_nothing
  2607 00010B52 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2608 00010B54 0F84781C0000        <1> 	je	sb16_stop
  2609                              <1> 	;cmp	al, 2 
  2610                              <1> 	;je	short ac97_stop
  2611 00010B5A E9A81F0000          <1> 	jmp	ac97_stop ; temporary.
  2612                              <1> 	;jmp	hda_stop
  2613                              <1> 
  2614                              <1> snd_nothing:
  2615                              <1> 	; 21/04/2017
  2616 00010B5F C3                  <1> 	retn
  2617                              <1> 
  2618                              <1> soundc_reset:
  2619                              <1> 	; FUNCTION = 8
  2620                              <1> 	; Reset Audio Controller
  2621                              <1> 	; 28/05/2017
  2622                              <1> 	; 22/04/2017
  2623 00010B60 E897020000          <1> 	call	snd_dev_check
  2624 00010B65 72F8                <1> 	jc	snd_nothing ; temporary.
  2625 00010B67 E89D020000          <1> 	call	snd_buf_check
  2626 00010B6C 72F1                <1> 	jc	snd_nothing ; temporary.	
  2627                              <1> 	
  2628 00010B6E A0[01710100]        <1> 	mov	al, [audio_device]
  2629 00010B73 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2630 00010B75 0F8427190000        <1> 	je	vt8233_reset
  2631 00010B7B 77E2                <1> 	ja	short snd_nothing ; temporary.
  2632                              <1> 	;ja	hda_reset	
  2633 00010B7D 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2634 00010B7F 0F8501200000        <1> 	jne	ac97_reset	
  2635 00010B85 E89A1C0000          <1> 	call	sb16_reset
  2636 00010B8A 0F822DFCFFFF        <1> 	jc	soundc_respond_err
  2637 00010B90 C3                  <1> 	retn
  2638                              <1> 
  2639                              <1> soundc_cancel:
  2640                              <1> 	; FUNCTION = 9
  2641                              <1> 	; Cancel audio callback service
  2642                              <1> 	; 22/04/2017
  2643 00010B91 A0[29710100]        <1> 	mov	al, [audio_user]	
  2644 00010B96 3A05[B3030300]      <1> 	cmp	al, [u.uno]
  2645 00010B9C 75C1                <1> 	jne	short snd_nothing
  2646                              <1> 	; RESET (audio) INTERRUPT CALLBACK SERVICE
  2647 00010B9E 8A1D[03710100]      <1> 	mov	bl, [audio_intr] ; IRQ number
  2648 00010BA4 A0[B3030300]        <1> 	mov	al, [u.uno]
  2649 00010BA9 28FF                <1> 	sub	bh, bh ; 0 ; unlink IRQ from user service
  2650 00010BAB E8EC020000          <1>  	call	set_irq_callback_service
  2651 00010BB0 0F8250FDFFFF        <1> 	jc	sndc_perm_error ; 'permission denied' error
  2652 00010BB6 C3                  <1> 	retn
  2653                              <1> 
  2654                              <1> sound_dalloc:
  2655                              <1> 	; FUNCTION = 10
  2656                              <1> 	; Deallocate (ring 3) audio buffer
  2657                              <1> 	; 22/04/2017
  2658 00010BB7 A0[29710100]        <1> 	mov	al, [audio_user]	
  2659 00010BBC 3A05[B3030300]      <1> 	cmp	al, [u.uno]
  2660 00010BC2 759B                <1> 	jne	short snd_nothing
  2661 00010BC4 8B1D[14710100]      <1> 	mov	ebx, [audio_buffer]
  2662                              <1> 	;or	ebx, ebx
  2663                              <1> 	;jz	short snd_nothing
  2664 00010BCA 8B0D[1C710100]      <1> 	mov	ecx, [audio_buff_size]
  2665 00010BD0 E81553FFFF          <1> 	call	deallocate_user_pages
  2666 00010BD5 31C0                <1> 	xor	eax, eax
  2667 00010BD7 A3[14710100]        <1> 	mov	[audio_buffer], eax ; 0
  2668 00010BDC A2[29710100]        <1> 	mov	[audio_user], al ; 0
  2669 00010BE1 C3                  <1> 	retn
  2670                              <1> 
  2671                              <1> sound_volume:
  2672                              <1> 	; FUNCTION = 11
  2673                              <1> 	; Set sound volume level
  2674                              <1> 	; 28/05/2017
  2675                              <1> 	; 20/05/2017
  2676                              <1> 	; 22/04/2017, 24/04/2017
  2677                              <1> 	; bl = component (0 = master/playback/lineout volume)
  2678                              <1> 	; cl = left channel volume level (0 to 31)
  2679                              <1> 	; ch = right channel volume level (0 to 31)
  2680                              <1> 
  2681 00010BE2 80FB80              <1> 	cmp	bl, 80h
  2682 00010BE5 720E                <1> 	jb	short snd_vol_1
  2683 00010BE7 0F8772FFFFFF        <1> 	ja	snd_nothing ; temporary.
  2684                              <1> 	; Set volume level for next play (BL>= 80h)
  2685 00010BED 66890D[36710100]    <1> 	mov	[audio_master_volume], cx
  2686 00010BF4 C3                  <1> 	retn
  2687                              <1> snd_vol_1:
  2688                              <1> 	; set volume level immediate (BL< 80h)
  2689 00010BF5 80FB00              <1> 	cmp	bl, 0
  2690 00010BF8 0F8761FFFFFF        <1> 	ja	snd_nothing ; temporary.
  2691                              <1> 
  2692 00010BFE E8F9010000          <1> 	call	snd_dev_check
  2693 00010C03 0F8256FFFFFF        <1> 	jc	snd_nothing ; temporary.
  2694 00010C09 E8FB010000          <1> 	call	snd_buf_check
  2695 00010C0E 0F824BFFFFFF        <1> 	jc	snd_nothing ; temporary.	
  2696                              <1> 
  2697 00010C14 A0[01710100]        <1> 	mov	al, [audio_device]
  2698 00010C19 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2699 00010C1B 0F849A180000        <1> 	je	vt8233_volume
  2700                              <1> 	; 28/05/2017
  2701 00010C21 0F8738FFFFFF        <1> 	ja	snd_nothing ; temporary.
  2702                              <1> 	;ja	hda_volume	
  2703                              <1> 	; Sound Blaster 16
  2704 00010C27 3C01                <1> 	cmp	al, 1 ; SB 16
  2705 00010C29 0F84281B0000        <1> 	je	sb16_volume
  2706 00010C2F E9E51D0000          <1> 	jmp	ac97_volume
  2707                              <1> 
  2708                              <1> soundc_disable:
  2709                              <1> 	; FUNCTION = 12 
  2710                              <1> 	; Disable audio device (and unlink DMA memory)
  2711                              <1> 	; 28/05/2017
  2712                              <1> 	; 24/05/2017
  2713                              <1> 	; 22/04/2017
  2714 00010C34 E8C3010000          <1> 	call	snd_dev_check
  2715 00010C39 0F8270FBFFFF        <1> 	jc	soundc_dev_err ; temporary.
  2716                              <1> 	;call	snd_buf_check
  2717                              <1> 	;jc	sndc_owner_error ; temporary.
  2718                              <1> 
  2719 00010C3F A0[01710100]        <1> 	mov	al, [audio_device]
  2720 00010C44 3C03                <1> 	cmp	al, 3 ; VIA VT 8237R (vt8233)
  2721 00010C46 7418                <1> 	je	short snd_disable_1
  2722 00010C48 0F8711FFFFFF        <1> 	ja	snd_nothing ; temporary.
  2723 00010C4E 3C01                <1> 	cmp	al, 1 ; Sound Blaster 16
  2724 00010C50 7507                <1> 	jne	short snd_disable_0
  2725 00010C52 E87B1B0000          <1> 	call	sb16_stop
  2726 00010C57 EB0C                <1> 	jmp	short snd_disable_2
  2727                              <1> snd_disable_0:
  2728 00010C59 E8A91E0000          <1> 	call	ac97_stop
  2729 00010C5E EB05                <1> 	jmp	short snd_disable_2
  2730                              <1> snd_disable_1:
  2731 00010C60 E838170000          <1> 	call	vt8233_stop
  2732                              <1> snd_disable_2:
  2733 00010C65 A0[03710100]        <1> 	mov	al, [audio_intr]
  2734 00010C6A 29DB                <1> 	sub	ebx, ebx ; 0 = reset
  2735 00010C6C E851FAFFFF          <1> 	call	set_dev_IRQ_service
  2736                              <1> 
  2737                              <1> 	;mov	al, [audio_intr]
  2738 00010C71 28E4                <1> 	sub	ah, ah ; 0 = reset
  2739 00010C73 E8B5F6FFFF          <1> 	call	set_hardware_int_vector
  2740                              <1> 
  2741 00010C78 31C0                <1> 	xor	eax, eax
  2742 00010C7A A2[01710100]        <1> 	mov	byte [audio_device], al
  2743 00010C7F A2[03710100]        <1> 	mov	byte [audio_intr], al
  2744 00010C84 8705[20710100]      <1> 	xchg	eax, [audio_dma_buff]
  2745                              <1> 	; 24/05/2017
  2746                              <1> 	;or	eax, eax
  2747                              <1> 	;jz	short snd_disable_3
  2748                              <1> 	;cmp	eax, sb16_dma_buffer ; default DMA buffer
  2749                              <1> 	;je	short snd_disable_3
  2750 00010C8A 803D[00710100]00    <1> 	cmp	byte [audio_pci], 0 ; AC97 audio controller ?
  2751 00010C91 7612                <1> 	jna	short snd_disable_3
  2752 00010C93 C605[00710100]00    <1> 	mov	byte [audio_pci], 0
  2753                              <1> 	;sub	ecx, ecx
  2754                              <1> 	;xchg	ecx, [audio_dmabuff_size]
  2755 00010C9A 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size]
  2756 00010CA0 E8F750FFFF          <1> 	call	deallocate_memory_block
  2757                              <1> snd_disable_3:
  2758 00010CA5 C3                  <1> 	retn
  2759                              <1> 
  2760                              <1> sound_dma_map:
  2761                              <1> 	; FUNCTION = 13 
  2762                              <1> 	; Map audio dma buff addr to user's buffer addr
  2763                              <1> 	; 12/05/2017
  2764 00010CA6 21C9                <1> 	and	ecx, ecx
  2765 00010CA8 0F8408FBFFFF        <1> 	jz	sound_buff_error
  2766 00010CAE 803D[01710100]01    <1> 	cmp	byte [audio_device], 1
  2767 00010CB5 7229                <1> 	jb	short snd_dma_map_1
  2768                              <1> snd_dma_map_0:
  2769 00010CB7 A1[20710100]        <1> 	mov	eax, [audio_dma_buff]
  2770 00010CBC 21C0                <1> 	and	eax, eax
  2771 00010CBE 7420                <1> 	jz	short snd_dma_map_1
  2772                              <1> 	;
  2773 00010CC0 8A1D[29710100]      <1> 	mov	bl, [audio_user]
  2774 00010CC6 08DB                <1> 	or	bl, bl
  2775 00010CC8 7416                <1> 	jz	short snd_dma_map_1
  2776 00010CCA 3A1D[B3030300]      <1> 	cmp	bl, [u.uno]
  2777 00010CD0 0F852BFCFFFF        <1> 	jne	sndc_owner_error
  2778                              <1> 	;
  2779 00010CD6 8B1D[24710100]      <1> 	mov	ebx, [audio_dmabuff_size]
  2780 00010CDC 21DB                <1> 	and	ebx, ebx
  2781 00010CDE 750A                <1> 	jnz	short snd_dma_map_2
  2782                              <1> snd_dma_map_1:
  2783 00010CE0 B8[00000200]        <1> 	mov	eax, sb16_dma_buffer
  2784 00010CE5 BB00000100          <1> 	mov	ebx, 65536
  2785                              <1> snd_dma_map_2:	
  2786 00010CEA 81C1FF0F0000        <1> 	add	ecx, PAGE_SIZE-1 ; 4095
  2787 00010CF0 6681E100F0          <1> 	and	cx, ~PAGE_OFF ; not 4095
  2788 00010CF5 39D9                <1> 	cmp	ecx, ebx
  2789 00010CF7 0F87B9FAFFFF        <1> 	ja	sound_buff_error
  2790 00010CFD 50                  <1> 	push	eax
  2791 00010CFE 89D3                <1> 	mov	ebx, edx
  2792 00010D00 C1E90C              <1> 	shr	ecx, 12 ; byte count to page count
  2793                              <1> 	; eax = physical address of (audio) dma buffer
  2794                              <1> 	; ebx = virtual address of (audio) dma buffer (user's pgdir) 
  2795                              <1> 	; ecx = page count (>0)
  2796 00010D03 E80451FFFF          <1> 	call	direct_memory_access
  2797 00010D08 58                  <1> 	pop	eax
  2798 00010D09 0F82A7FAFFFF        <1> 	jc	sound_buff_error
  2799 00010D0F A3[64030300]        <1> 	mov	[u.r0], eax
  2800 00010D14 C3                  <1> 	retn
  2801                              <1> 
  2802                              <1> soundc_info:
  2803                              <1> 	; FUNCTION = 14 
  2804                              <1> 	; Get Audio Controller Info
  2805                              <1> 	; 10/06/2017
  2806                              <1> 	; 05/06/2017
  2807 00010D15 20DB                <1> 	and	bl, bl ; 0
  2808 00010D17 740A                <1> 	jz	short sndc_info_0
  2809                              <1> 	; invalid parameter !
  2810 00010D19 B817000000          <1> 	mov	eax, ERR_INV_PARAMETER ; 23
  2811                              <1> ;sndc_inf_error:
  2812                              <1> ;	mov	[u.r0], eax
  2813                              <1> ;	mov	[u.error], eax
  2814                              <1> ;	jmp	error
  2815 00010D1E E99FFAFFFF          <1> 	jmp	sysaudio_err
  2816                              <1> 
  2817                              <1> sndc_info_0:
  2818 00010D23 E8D4000000          <1> 	call	snd_dev_check
  2819 00010D28 0F8281FAFFFF        <1> 	jc	soundc_dev_err
  2820                              <1> 
  2821 00010D2E 8B1D[0C710100]      <1> 	mov	ebx, [audio_vendor]
  2822 00010D34 8B0D[08710100]      <1> 	mov	ecx, [audio_dev_id]
  2823                              <1> 	;mov	al,  [audio_device]
  2824 00010D3A 3C02                <1> 	cmp	al, 2 ; AC'97 (ICH)
  2825 00010D3C 7513                <1> 	jne	short sndc_info_1
  2826                              <1> 	; Intel AC97 (ICH) Audio Controller (=2)	
  2827 00010D3E 668B15[3A710100]    <1> 	mov	dx, [NABMBAR]
  2828 00010D45 C1E210              <1> 	shl	edx, 16
  2829 00010D48 668B15[38710100]    <1> 	mov	dx, [NAMBAR]
  2830 00010D4F EB07                <1> 	jmp	short sndc_info_2
  2831                              <1> sndc_info_1:
  2832                              <1> 	; 05/06/2017
  2833                              <1> 	; Note: Intel HDA code (here) is not ready yet!
  2834                              <1> 	; !!! SB16 or VT8233 (VT8237R) !!!
  2835 00010D51 0FB715[06710100]    <1> 	movzx	edx, word [audio_io_base]	
  2836                              <1> sndc_info_2:
  2837 00010D58 88C4                <1> 	mov	ah, al ;  [audio_device]
  2838 00010D5A A0[03710100]        <1> 	mov	al, [audio_intr] 
  2839                              <1> 
  2840                              <1> 	; EAX = IRQ Number in AL
  2841                              <1> 	;	Audio Device Number in AH 
  2842                              <1> 	; EBX = DEV/VENDOR ID
  2843                              <1> 	;	(DDDDDDDDDDDDDDDDVVVVVVVVVVVVVVVV)
  2844                              <1> 	; ECX = BUS/DEV/FN 
  2845                              <1> 	;	(00000000BBBBBBBBDDDDDFFF00000000)
  2846                              <1> 	; EDX = NABMBAR/NAMBAR (for AC97)
  2847                              <1> 	;	(Low word, DX = NAMBAR address)
  2848                              <1> 	; EDX = Base IO Addr (DX) for SB16 & VT8233
  2849                              <1> 
  2850                              <1> 	; 10/06/2017
  2851 00010D5F A3[64030300]        <1> 	mov	[u.r0], eax
  2852 00010D64 8B2D[60030300]      <1> 	mov	ebp, [u.usp]
  2853 00010D6A 895D10              <1> 	mov	[ebp+16], ebx  ; ebx
  2854 00010D6D 895514              <1> 	mov	[ebp+20], edx  ; edx
  2855 00010D70 894D18              <1> 	mov	[ebp+24], ecx  ; ecx
  2856                              <1>   			  		
  2857 00010D73 C3                  <1>  	retn
  2858                              <1> 
  2859                              <1> sound_data:
  2860                              <1> 	; FUNCTION = 15 
  2861                              <1> 	; Get Current Sound data for graphics
  2862                              <1> 	; 22/06/2017
  2863                              <1> 	;
  2864 00010D74 E883000000          <1> 	call	snd_dev_check
  2865 00010D79 0F8230FAFFFF        <1> 	jc	soundc_dev_err ; Device not ready !
  2866                              <1> 
  2867 00010D7F 80FB00              <1> 	cmp	bl, 0
  2868 00010D82 760A                <1> 	jna	short sound_data_0
  2869                              <1> 
  2870                              <1> 	; Only PCM OUT buffer data is valid for now!
  2871 00010D84 B817000000          <1> 	mov	eax, ERR_INV_PARAMETER  ; 23
  2872 00010D89 E934FAFFFF          <1> 	jmp	sysaudio_err
  2873                              <1> 
  2874                              <1> sound_data_0:
  2875 00010D8E A1[20710100]        <1> 	mov	eax, [audio_dma_buff]
  2876 00010D93 09C0                <1> 	or	eax, eax
  2877 00010D95 0F841BFAFFFF        <1> 	jz	sound_buff_error
  2878                              <1> 
  2879 00010D9B 803D[01710100]04    <1> 	cmp	byte [audio_device], 4 ; Intel HDA
  2880 00010DA2 744F                <1> 	je	short sound_data_4 ; temporary ! (22/06/2017)
  2881                              <1> 
  2882 00010DA4 21C9                <1> 	and	ecx, ecx
  2883                              <1> 	;jnz	short sound_data_1 ; sample tranfer
  2884                              <1> 	
  2885                              <1> 	; Return only DMA Buffer pointer/offset... 
  2886                              <1> 	; (If DMA Buffer has been mapped to user's
  2887                              <1> 	;  memory space; program can get graphics
  2888                              <1> 	;  data by using only this pointer value.)
  2889                              <1> 	   	
  2890                              <1> 	;call	get_dma_buffer_offset
  2891                              <1> 	;; eax = DMA buffer offset
  2892                              <1> 	;;	(!not half buffer offset!)
  2893                              <1> 	;mov	[u.r0], eax
  2894                              <1> 	;retn
  2895                              <1> 
  2896 00010DA6 0F84521F0000        <1> 	jz	get_dma_buffer_offset	
  2897                              <1> 	
  2898                              <1> sound_data_1:
  2899                              <1> 	;mov	eax, [audio_dmabuff_size]
  2900                              <1> 	;shr	eax, 1 ; half buffer size
  2901                              <1> 	;cmp	ecx, eax
  2902                              <1> 	;ja	short sound_buff_error	
  2903                              <1> 
  2904 00010DAC 3B0D[24710100]      <1> 	cmp	ecx, [audio_dmabuff_size]
  2905 00010DB2 0F87FEF9FFFF        <1> 	ja	sound_buff_error
  2906                              <1> 
  2907 00010DB8 89D0                <1> 	mov	eax, edx
  2908 00010DBA 25FF0F0000          <1> 	and	eax, PAGE_OFF ; 4095 (0FFFh)
  2909 00010DBF 81F900100000        <1> 	cmp	ecx, 4096
  2910 00010DC5 7605                <1> 	jna	short sound_data_2
  2911 00010DC7 B900100000          <1> 	mov	ecx, 4096 ; max. 1 page
  2912                              <1> sound_data_2:
  2913 00010DCC 01C8                <1> 	add	eax, ecx
  2914 00010DCE 3D00100000          <1> 	cmp	eax, 4096
  2915 00010DD3 7606                <1> 	jna	short sound_data_3
  2916 00010DD5 6625FF0F            <1> 	and	ax, PAGE_OFF ; 4095 (0FFFh)
  2917 00010DD9 29C1                <1> 	sub	ecx, eax
  2918                              <1> 	; here, ECX has been adjusted to fit 
  2919                              <1> 	;	in page border..  (<= 4096, >0)
  2920                              <1> sound_data_3:
  2921 00010DDB 51                  <1> 	push	ecx
  2922 00010DDC 52                  <1> 	push	edx
  2923 00010DDD 89D3                <1> 	mov	ebx, edx 
  2924 00010DDF E8164CFFFF          <1> 	call	get_physical_addr
  2925 00010DE4 5A                  <1> 	pop	edx
  2926 00010DE5 59                  <1> 	pop	ecx
  2927 00010DE6 0F82CAF9FFFF        <1> 	jc	sound_buff_error	
  2928                              <1> 	
  2929                              <1> 	; eax = physical address of user's buffer
  2930 00010DEC 89C3                <1> 	mov	ebx, eax  
  2931                              <1> 	; ecx = byte (transfer) count
  2932                              <1> 	;call	get_current_sound_data
  2933                              <1> 	;retn
  2934 00010DEE E9681E0000          <1> 	jmp	get_current_sound_data
  2935                              <1> 
  2936                              <1> sound_data_4:
  2937                              <1> 	; Intel HDA code is not ready yet !
  2938                              <1> 	; 22/06/2017
  2939 00010DF3 31C0                <1> 	xor	eax, eax
  2940 00010DF5 48                  <1> 	dec	eax
  2941 00010DF6 A3[64030300]        <1> 	mov	[u.r0], eax ; 0FFFFFFFFh
  2942 00010DFB C3                  <1> 	retn 
  2943                              <1> 
  2944                              <1> snd_dev_check:
  2945                              <1> 	; 10/06/2017
  2946                              <1> 	; 05/06/2017
  2947                              <1> 	; 24/05/2017
  2948                              <1> 	; 22/04/2017
  2949                              <1> 	; 21/04/2017
  2950                              <1> 	; ... device check at first
  2951 00010DFC A0[01710100]        <1> 	mov	al, [audio_device]
  2952 00010E01 3C01                <1> 	cmp	al, 1 ; SB 16
  2953 00010E03 7203                <1> 	jb	short snd_dev_chk_retn ; error !
  2954                              <1> 	;cmp	al, 4 ; Intel HDA
  2955                              <1> 	;ja	short snd_dbchk_stc ; invalid !
  2956                              <1> 	; 10/06/2017
  2957 00010E05 3C05                <1> 	cmp	al, 5
  2958 00010E07 F5                  <1> 	cmc
  2959                              <1> snd_dev_chk_retn:
  2960 00010E08 C3                  <1> 	retn
  2961                              <1> 
  2962                              <1> snd_buf_check:
  2963                              <1> 	; 10/06/2017
  2964                              <1> 	; 22/04/2017
  2965                              <1> 	; 21/04/2017
  2966                              <1> 	; ... buffer & (buffer) owner check at second
  2967 00010E09 833D[14710100]00    <1> 	cmp	dword [audio_buffer], 0
  2968 00010E10 760D                <1> 	jna	short snd_dbchk_stc
  2969                              <1> snd_user_check:
  2970 00010E12 A0[B3030300]        <1> 	mov	al, [u.uno]
  2971 00010E17 3A05[29710100]      <1> 	cmp	al, [audio_user]
  2972                              <1> 	;jne	short snd_dbchk_stc
  2973                              <1> 	;retn
  2974 00010E1D 74E9                <1> 	je	short snd_dev_chk_retn
  2975                              <1> 
  2976                              <1> snd_dbchk_stc:
  2977 00010E1F F9                  <1> 	stc
  2978 00010E20 C3                  <1> 	retn
  2979                              <1> 
  2980                              <1> sound_update:
  2981                              <1> 	; FUNCTION = 16 
  2982                              <1> 	; bl = 
  2983                              <1> 	;    0 = automatic (sequental) update (with flag switch!)
  2984                              <1> 	;    1 = update dma half buffer 1 (without flag switch!)		
  2985                              <1> 	;    2 = update dma half buffer 2 (without flag switch!)
  2986                              <1> 	;  FFh = get current flag value	
  2987                              <1> 	;      0 = dma half buffer 1 (will be played next)
  2988                              <1> 	;      1 = dma half buffer 2 (will be played next)
  2989                              <1> 	
  2990                              <1> 	; 10/10/2017
  2991                              <1> 	
  2992                              <1> 	; ... device check at first
  2993 00010E21 A0[01710100]        <1> 	mov	al, [audio_device]
  2994 00010E26 08C0                <1> 	or	al, al ; 0 ; pc speaker or invalid 
  2995 00010E28 0F8481F9FFFF        <1> 	jz	soundc_dev_err
  2996                              <1> 
  2997                              <1> 	; ... buffer & (buffer) owner check at second
  2998 00010E2E 833D[14710100]00    <1> 	cmp	dword [audio_buffer], 0
  2999 00010E35 0F867BF9FFFF        <1> 	jna	sound_buff_error
  3000 00010E3B A0[B3030300]        <1> 	mov	al, [u.uno]
  3001 00010E40 3A05[29710100]      <1> 	cmp	al, [audio_user]
  3002 00010E46 0F85B5FAFFFF        <1> 	jne	sndc_owner_error
  3003                              <1> 
  3004                              <1> 	; Transfer ring 3 (user's) audio buffer content to dma buffer
  3005 00010E4C 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff] ; dma buffer (ring 0)
  3006 00010E52 09FF                <1> 	or	edi, edi
  3007 00010E54 0F845CF9FFFF        <1> 	jz	sound_buff_error
  3008 00010E5A 8B35[18710100]      <1> 	mov	esi, [audio_p_buffer] ; physical address (ring 3)
  3009 00010E60 8B0D[1C710100]      <1> 	mov	ecx, [audio_buff_size]
  3010                              <1> 	
  3011                              <1> 	;movzx	eax, byte [audio_flag]
  3012 00010E66 A0[28710100]        <1> 	mov	al, [audio_flag]
  3013                              <1> 
  3014 00010E6B FEC3                <1> 	inc	bl
  3015 00010E6D 7427                <1> 	jz	short snd_update_3 ; bl = 0FFh
  3016 00010E6F FECB                <1> 	dec	bl 
  3017 00010E71 7411                <1> 	jz	short snd_update_0 ; bl = 0
  3018                              <1> 
  3019 00010E73 80FB02              <1> 	cmp	bl, 2
  3020 00010E76 7417                <1> 	je	short snd_update_1 ; dma half buffer 2
  3021 00010E78 7217                <1> 	jb	short snd_update_2 ; dma half buffer 1
  3022                              <1>  
  3023                              <1> 	; invalid parameter !
  3024 00010E7A B817000000          <1> 	mov	eax, ERR_INV_PARAMETER ; 23
  3025                              <1> ;	mov	[u.r0], eax
  3026                              <1> ;	mov	[u.error], eax
  3027                              <1> ;	jmp	error
  3028 00010E7F E93EF9FFFF          <1> 	jmp	sysaudio_err
  3029                              <1> 	
  3030                              <1> snd_update_0:
  3031 00010E84 8035[28710100]01    <1> 	xor	byte [audio_flag], 1 ; update flag !!!
  3032 00010E8B 3C01                <1> 	cmp	al, 1
  3033 00010E8D 7202                <1> 	jb	short snd_update_2 ; dma half buffer 1
  3034                              <1> snd_update_1:
  3035                              <1> 	; dma half buffer 2
  3036 00010E8F 01CF                <1> 	add	edi, ecx
  3037                              <1> snd_update_2:
  3038                              <1> 	;rep	movsb
  3039 00010E91 C1E902              <1> 	shr	ecx, 2
  3040 00010E94 F3A5                <1> 	rep	movsd
  3041                              <1> snd_update_3:
  3042 00010E96 A3[64030300]        <1> 	mov	[u.r0], eax
  3043                              <1> 
  3044 00010E9B C3                  <1> 	retn
  3045                              <1> 	
  3046                              <1> set_irq_callback_service:
  3047                              <1> 	; 03/08/2020
  3048                              <1> 	; 10/06/2017
  3049                              <1> 	; 12/05/2017
  3050                              <1> 	; 24/04/2017
  3051                              <1> 	; 22/04/2017
  3052                              <1> 	; caller: 'syscalbac' or 'sysaudio' or ...
  3053                              <1> 	; 13/04/2017, 14/04/2017, 17/04/2017
  3054                              <1> 	; 24/02/2017, 26/02/2017, 28/02/2017
  3055                              <1> 	; 21/02/2017 - TRDOS 386 (TRDOS v2.0)
  3056                              <1> 	;
  3057                              <1> 	; Link or unlink IRQ callback service to/from user (ring 3)	
  3058                              <1> 	;
  3059                              <1> 	; INPUT ->
  3060                              <1> 	;	If AL = 0, the caller is 'syscalbac';
  3061                              <1> 	;	   otherwise, the caller is 'sysaudio' or ...
  3062                              <1> 	;	   (AL = user number) 
  3063                              <1> 	; 	 
  3064                              <1> 	;	BL = IRQ number (Hardware interrupt request number)
  3065                              <1> 	;	     (0 t0 15 but IRQ 0,1,2,6,8,14,15 are prohibited)
  3066                              <1> 	;	     IRQ numbers 3,4,5,7,9,10,11,12,13 are valid
  3067                              <1> 	;	     (numbers >15 are invalid)
  3068                              <1> 	;
  3069                              <1> 	;	BH = 0 = Unlink IRQ (in BL) from user (ring 3) service
  3070                              <1> 	;	     1 = Link IRQ by using Signal Response Byte method
  3071                              <1> 	;	     2 = Link IRQ by using Callback service method 		
  3072                              <1> 	;	     3 = Link IRQ by using Auto Increment S.R.B. method 	
  3073                              <1> 	;	    >3 = invalid 
  3074                              <1> 	;		 (syscallback version will return to user) 	
  3075                              <1> 	;	
  3076                              <1> 	;	CL = Signal Return/Response Byte value 
  3077                              <1> 	;
  3078                              <1> 	;	If BH = 3, kernel will put a counter value ; 03/08/2020
  3079                              <1> 	;	          (into the S.R.B. addr)
  3080                              <1> 	;		  between 0 to 255. (start value = CL+1)
  3081                              <1> 	;	
  3082                              <1> 	;	NOTE: counter value, for example: even and odd numbers
  3083                              <1> 	;	      may be used for -audio- DMA buffer switch 
  3084                              <1> 	;	      within double buffer method, etc. 		
  3085                              <1> 	;
  3086                              <1> 	;	EDX = Signal return (Response) byte address
  3087                              <1> 	;	       		  - or -
  3088                              <1> 	;	      Interrupt/Callback service/routine address
  3089                              <1> 	; 	
  3090                              <1> 	;	      (virtual address in user's memory space)
  3091                              <1> 	;
  3092                              <1> 	; OUTPUT ->
  3093                              <1> 	;	CF = 0 & EAX = 0 -> Successful setting
  3094                              <1> 	;	CF = 1 & EAX > 0 -> IRQ is prohibited or locked 
  3095                              <1> 	;			by another process
  3096                              <1> 	;		 eax = ERR_PERM_DENIED -> prohibited or locked
  3097                              <1> 	;		 eax = ERR_INV_PARAMETER -> 
  3098                              <1> 	;		       invalid parameter/option or bad address
  3099                              <1> 	;
  3100                              <1> 	; TRDOS 386 - IRQ CALLBACK structures (parameters):
  3101                              <1> 	;	
  3102                              <1> 	;	   [u.irqlock] = 1 word, IRQ flags (0-15) that indicates
  3103                              <1> 	;			which IRQs are locked by (that) user.
  3104                              <1> 	;		        Lock and unlock (by user) will change
  3105                              <1> 	;			these flags or 'terminate process' (sysexit)
  3106                              <1> 	;			will clear these flags and unlock those IRQs.
  3107                              <1> 	;			               
  3108                              <1> 	;		   	Bit 0 is for IRQ 0 and Bit 15 is for IRQ 15
  3109                              <1> 	;
  3110                              <1> 	;	   IRQ(x).owner	 : 1 byte, user, [u.uno], 0 = free (unlocked)	
  3111                              <1> 	;
  3112                              <1> 	;	   IRQ(x).method : 1 byte for callback method & status
  3113                              <1> 	;			   0 = Signal Response Byte method
  3114                              <1> 	;			   1 = Callback service method
  3115                              <1> 	;			   >1 = invalid for current 'syscalback'.
  3116                              <1> 	;			or(+) 80h = IRQ is in use by system (ring 0)
  3117                              <1> 	;			            function (audio etc.) or
  3118                              <1> 	;			   	    a device driver.	   	
  3119                              <1> 	;			(system function will ignore the lock/owner)
  3120                              <1> 	;
  3121                              <1> 	;	   IRQ(x).srb	: 1 byte, Signal Return/Response byte value
  3122                              <1> 	;			  (a fixed value by user or a counter value
  3123                              <1> 	;			 from 0 to 255, which is increased by every
  3124                              <1> 	;			 interrupt just before putting it into 
  3125                              <1> 	;			 the Signal Response byte address
  3126                              <1> 	;			 (This is not used in callback serv method)
  3127                              <1> 	;	    	  
  3128                              <1> 	;	   IRQ(x).addr	: 1 dword
  3129                              <1> 	;			  Signal Response Byte address (physical)
  3130                              <1> 	;			  		-or-
  3131                              <1> 	;			  Callback service address (virtual)
  3132                              <1> 	;
  3133                              <1> 	;	   IRQ(x).dev	: 1 byte
  3134                              <1> 	;			  0 = Default device or kernel function
  3135                              <1> 	;			  		-or-
  3136                              <1> 	;			  1-255 = Assigned device driver number
  3137                              <1> 	;
  3138                              <1> 	;	   (x) = 3,4,5,7,9,10,11,12,13
  3139                              <1> 	;
  3140                              <1> 	
  3141 00010E9C 80FB0F              <1> 	cmp	bl, 15
  3142 00010E9F 7729                <1> 	ja	short scbs_2
  3143                              <1> 	
  3144 00010EA1 80FF03              <1> 	cmp	bh, 3
  3145 00010EA4 7724                <1> 	ja	short scbs_2  ; invalid parameter
  3146                              <1> 
  3147 00010EA6 0FB6FB              <1> 	movzx	edi, bl ; save IRQ number
  3148                              <1> 
  3149                              <1> 		;  IRQ 0,1,2,6,8,14,15 are prohibited
  3150                              <1> 	;IRQenum: ; 'trdosk9.s'
  3151                              <1> 	;	db  0,0,0,1,2,3,0,4,0,5,6,7,8,9,0,0
  3152                              <1> 
  3153 00010EA9 0FB6B7[FC1B0100]    <1> 	movzx	esi, byte [edi+IRQenum] ; IRQ availability 
  3154                              <1> 					; enumeration/index
  3155                              <1> 	;dec	esi
  3156 00010EB0 664E                <1> 	dec	si
  3157 00010EB2 780F                <1> 	js	short scbs_1 ;  0 -> 0FFFFh  
  3158                              <1> 
  3159                              <1> 	; ESI = IRQ callback parameters index number (0 to 8)
  3160                              <1> 
  3161 00010EB4 08FF                <1> 	or	bh, bh
  3162 00010EB6 7419                <1> 	jz	short scbs_4 ; unlink the IRQ (in BL)
  3163                              <1> 
  3164 00010EB8 FECF                <1> 	dec	bh
  3165                              <1> 	; bh = method (0 = signal response byte, 1 = callback)
  3166                              <1> 	;	      (2 = auto increment of signal response byte) 
  3167                              <1> 
  3168 00010EBA 80BE[B2700100]00    <1> 	cmp	byte [esi+IRQ.owner], 0 ; locked ?
  3169 00010EC1 7637                <1> 	jna	short scbs_6	; no... OK...	
  3170                              <1> 
  3171                              <1> scbs_1:
  3172                              <1> 	; permission denied (prohibited IRQ)
  3173 00010EC3 B80B000000          <1> 	mov	eax, ERR_PERM_DENIED
  3174 00010EC8 F9                  <1> 	stc
  3175 00010EC9 C3                  <1> 	retn
  3176                              <1> scbs_2:
  3177 00010ECA F9                  <1> 	stc
  3178                              <1> scbs_3:
  3179 00010ECB B817000000          <1> 	mov	eax, ERR_INV_PARAMETER
  3180 00010ED0 C3                  <1> 	retn
  3181                              <1> 
  3182                              <1> scbs_4: ; unlink the requested IRQ (if it belongs to current user)
  3183                              <1> 	; 10/06/2017
  3184                              <1> 	; 22/04/2017
  3185                              <1> 	; 14/04/2017
  3186                              <1> 	; If AL = 0 -> The caller is 'syscalbac'
  3187 00010ED1 8AA6[B2700100]      <1> 	mov	ah, [esi+IRQ.owner]
  3188 00010ED7 3A25[B3030300]      <1> 	cmp	ah, [u.uno]
  3189 00010EDD 75E4                <1> 	jne	short scbs_1
  3190                              <1> 
  3191 00010EDF FE0D[D6030300]      <1> 	dec	byte [u.irqc] ; decrease IRQ count (in use)
  3192                              <1> 
  3193                              <1> 	;sub	ah, ah
  3194                              <1> 	;mov	[esi+IRQ.owner], ah ; 0 ; free !!!
  3195                              <1> 	;and	byte [esi+IRQ.method], 80h
  3196                              <1> 	;mov	[esi+IRQ.srb], ah ; 0
  3197                              <1> 	;mov	[esi+IRQ.dev], ah ; 0
  3198                              <1> 	;mov	dword [esi+IRQ.addr], 0
  3199                              <1> 	;mov	dword [u.r0], 0
  3200                              <1> 
  3201                              <1> 	;mov	byte [esi+IRQ.owner], 0
  3202                              <1> 
  3203                              <1> 	; 22/04/2017
  3204 00010EE5 29C0                <1> 	sub	eax, eax
  3205 00010EE7 8886[B2700100]      <1> 	mov	[esi+IRQ.owner], al ; 0
  3206                              <1> 	; 10/06/2017
  3207 00010EED 8686[C4700100]      <1> 	xchg	al, [esi+IRQ.method]
  3208 00010EF3 2480                <1> 	and	al, 80h
  3209 00010EF5 745E                <1> 	jz	short scbs_12 
  3210                              <1> 	; Audio device must be disabled -later- ! ([IRQ.medhod] = 80h)
  3211                              <1> 
  3212                              <1> ;	cmp	byte [esi+IRQ.method], 80h ; device drv or kernel extension ?
  3213                              <1> ;	jb	short scbs_12 ; bh = 0 reset to default IRQ handler
  3214                              <1> ;
  3215                              <1> ;	and	al, al
  3216                              <1> ;	jz	short  scbs_5  ; the caller is 'syscalbac'
  3217                              <1> ;	; The caller is 'sysaudio' or ...
  3218 00010EF7 30C0                <1> 	xor	al, al
  3219                              <1> ;	mov	[esi+IRQ.method], al ; 0 ; reset kernel extension flag
  3220                              <1> ;scbs_5:
  3221                              <1> ;	sub	ah, ah
  3222                              <1> 	;mov	[u.r0], eax ; 0
  3223 00010EF9 C3                  <1> 	retn	
  3224                              <1> 
  3225                              <1> scbs_6:
  3226                              <1> 	; 14/04/2017
  3227 00010EFA 20C0                <1> 	and	al, al
  3228 00010EFC 7405                <1> 	jz	short scbs_7  ; the caller is 'syscalbac'
  3229                              <1> 	; AL = user number ([u.uno] or [audio.user] or ...)
  3230                              <1> 	; The caller is 'sysaudio' or ...
  3231                              <1> 	;	
  3232                              <1> 	; bh = method (0 = signal response byte, 1 = callback)
  3233                              <1> 	;	      (2 = auto increment of signal response byte) 
  3234                              <1> 
  3235 00010EFE 80CF80              <1> 	or	bh, 80h		; Kernel extension flag !
  3236 00010F01 EB0A                <1> 	jmp	short scbs_8
  3237                              <1> scbs_7:	
  3238 00010F03 8A86[C4700100]      <1> 	mov	al, [esi+IRQ.method] ; >= 80h = kernel is using this IRQ
  3239 00010F09 2480                <1> 	and	al, 80h ; use only bit 7 (kernel function flag)
  3240 00010F0B 08C7                <1> 	or	bh, al		 ; method 
  3241                              <1> 				 ; 0 = signal response byte, 1 = callback
  3242                              <1> 				 ; 2 = auto increment of s.r.b.
  3243                              <1> scbs_8:
  3244 00010F0D A0[B3030300]        <1> 	mov	al, [u.uno] ; user (process) number (1 to 16)
  3245 00010F12 8886[B2700100]      <1> 	mov	[esi+IRQ.owner], al ; lock the IRQ for user
  3246 00010F18 88BE[C4700100]      <1> 	mov	[esi+IRQ.method], bh
  3247                              <1> 
  3248                              <1> ;	test	bh, 1
  3249                              <1> ;	jnz	short scbs_9 	 ; Callback method, CX will not be used 
  3250                              <1> ;			
  3251                              <1> ;	test	bh, 2		 ; use auto increment (counter) method
  3252                              <1> ;	jz	short scbs_10	 ; (count can be used for buffer switch)
  3253                              <1> ;scbs_9:
  3254                              <1> ;	xor	ecx, ecx ; 0
  3255                              <1> scbs_10:			      	
  3256                              <1> 	;mov	[esi+IRQ.method], bh
  3257 00010F1E 888E[CD700100]      <1> 	mov	[esi+IRQ.srb], cl
  3258 00010F24 C686[BB700100]00    <1> 	mov	byte [esi+IRQ.dev], 0 ; device number is always 0 
  3259                              <1> 				 ; for this system call
  3260                              <1> 	;test	bh, 1
  3261 00010F2B 80E701              <1> 	and	bh, 1 ; 17/04/2017
  3262 00010F2E 7513                <1> 	jnz	short scbs_11	 ; callback method, use virtual address 
  3263                              <1> 
  3264 00010F30 53                  <1> 	push	ebx ; IRQ number (in BL)
  3265 00010F31 89D3                <1> 	mov	ebx, edx
  3266                              <1> 	; ebx = virtual address
  3267                              <1> 	; [u.pgdir] = page directory's physical address
  3268 00010F33 FE05[52700100]      <1> 	inc	 byte [no_page_swap] ; 1 
  3269                              <1> 			; Do not add this page to swap queue
  3270                              <1> 			; and remove it from swap queue if it is
  3271                              <1> 			; on the queue.
  3272 00010F39 E8BC4AFFFF          <1> 	call	get_physical_addr
  3273 00010F3E 5B                  <1> 	pop	ebx
  3274 00010F3F 728A                <1> 	jc	scbs_3 ; invalid address !
  3275                              <1> 	; eax = physical address of the virtual address in user's space
  3276 00010F41 89C2                <1> 	mov	edx, eax
  3277                              <1> scbs_11:
  3278 00010F43 66C1E602            <1> 	shl	si, 2		; byte (index) to dword (offset)
  3279 00010F47 8996[D6700100]      <1> 	mov	[esi+IRQ.addr], edx
  3280                              <1> 
  3281 00010F4D FE05[D6030300]      <1> 	inc	byte [u.irqc]	; increase IRQ (in use) count
  3282                              <1> 
  3283 00010F53 FEC7                <1> 	inc	 bh ; 17/04/2017
  3284                              <1> 	; bh > 0 -> set to requested IRQ handler (IRQ_u_list)
  3285                              <1> scbs_12:
  3286 00010F55 88D8                <1> 	mov	al, bl ; IRQ number
  3287 00010F57 88FC                <1> 	mov	ah, bh ; 0 = reset, >0 = set
  3288 00010F59 E8CFF3FFFF          <1> 	call	set_hardware_int_vector
  3289                              <1> 
  3290 00010F5E 31C0                <1> 	xor	eax, eax
  3291                              <1> 	;mov 	[u.r0], eax ; 0	
  3292                              <1> 
  3293 00010F60 C3                  <1> 	retn	; return with success (cf=0, eax=0)
  3294                              <1> 
  3295                              <1> 
  3296                              <1> sysdma: ; DMA FUNCTIONS
  3297                              <1> 	; 02/09/2017
  3298                              <1> 	; 28/08/2017
  3299                              <1> 	; 20/08/2017 - TRDOS 386 (TRDOS v2.0)
  3300                              <1> 	;
  3301                              <1> 	; Inputs:
  3302                              <1> 	;	BH = 0 -> Allocate DMA buffer
  3303                              <1> 	;	   BL = 0 -> Use the system's default DMA
  3304                              <1> 	;		     (SB16) Buffer
  3305                              <1> 	;	        Buffer Size (max.) = 65536 bytes
  3306                              <1> 	;	   BL > 0 -> Allocate (a new) DMA buffer
  3307                              <1>  	;	   ECX = DMA Buffer Size in bytes (<=128KB)
  3308                              <1> 	;	   EDX = Virtual Address of DMA buffer 	
  3309                              <1> 	;		
  3310                              <1> 	;	BH = 1 -> Initialize (Start) DMA service
  3311                              <1> 	;	     BL, bit 0 to 3 = Channel Number (0 to 7)	
  3312                              <1> 	;	     BL, bit 7 = Auto Initialized Mode 
  3313                              <1> 	;			(If bit 7 is set)
  3314                              <1> 	;		 bit 6 = Record (read) mode (0= playback)
  3315                              <1> 	;	     ECX = byte count (0 = use dma buffer size)
  3316                              <1> 	;	     EDX = physical buffer address
  3317                              <1> 	;	     	   (0 = use dma buffer -start- address)		
  3318                              <1> 	;
  3319                              <1> 	;	BH = 2 -> Get Current DMA Buffer Offset
  3320                              <1> 	;	     BL = DMA channel number	
  3321                              <1> 	;		
  3322                              <1> 	;	BH = 3 -> Get Current DMA count down value
  3323                              <1> 	;	     BL = DMA channel number (0 tO 7)	
  3324                              <1> 	;
  3325                              <1> 	;	BH = 4 -> Get Current DMA channel (in progress)
  3326                              <1> 	;
  3327                              <1> 	;	BH = 5 -> Get System's Default DMA Buffer Address
  3328                              <1> 	;
  3329                              <1> 	;	BH = 6 -> Get Current DMA Buffer Address	
  3330                              <1> 	;
  3331                              <1> 	;	BH = 7 -> Stop DMA service
  3332                              <1> 	;
  3333                              <1> 	;
  3334                              <1> 	; Outputs:
  3335                              <1> 	;
  3336                              <1> 	;	For BH = 0 ; Allocate DMA buffer
  3337                              <1> 	;	    EAX = Physical address of DMA buffer
  3338                              <1> 	;	    ECX = Allocated buffer size in bytes
  3339                              <1> 	;		  - page count * 4096 -
  3340                              <1> 	;		  (may be bigger than requested)	
  3341                              <1> 	;	    If BL input > 0,
  3342                              <1> 	;	       'sysalloc:' system call will be used with
  3343                              <1>   	;	       EBX (for 'sysalloc') = EDX (for 'sysdma')
  3344                              <1> 	;	       ECX is same, byte count (buffer size)
  3345                              <1> 	;	       EDX = 1024*1024*16 ; 16 MB upper limit	 		        	 
  3346                              <1> 	;	    If BL input = 0,
  3347                              <1> 	;	       Default DMA buffer (SB16 buffer) will be
  3348                              <1> 	;	       checked and if it is free, it's address
  3349                              <1> 	;	       will be returned in EAX and it's size
  3350                              <1> 	;	       will be returned in ECX (as 65536)
  3351                              <1> 	;
  3352                              <1> 	;	    If CF = 1, error code is in EAX
  3353                              <1> 	;	       EAX = -1 ; DMA buffer allocation error! 		
  3354                              <1> 	;	       EAX = 11 ; 'Permission Denied' error !
  3355                              <1> 	;
  3356                              <1> 	;	       Note: 'sysalloc' error return method
  3357                              <1> 	;		      will be applied if BL input > 0 !		
  3358                              <1> 	;
  3359                              <1> 	; 	 For BH = 1 ; Initialize (Start) DMA
  3360                              <1> 	;	     EAX = 0 (Successful)	
  3361                              <1> 	;	     If CF = 1, error code is in EAX
  3362                              <1> 	;
  3363                              <1> 	; 	 For BH = 2 ; Get Current DMA Buffer Offset
  3364                              <1> 	;	     EAX = DMA Buffer Offset (in bytes)
  3365                              <1> 	;	     ;
  3366                              <1> 	;	      AX = DMA buffer offset
  3367                              <1> 	;	     EAX bits 16 to 23 = Page register value
  3368                              <1> 	;		   	
  3369                              <1> 	; 	 For BH = 3 ; Get Current DMA count down value
  3370                              <1> 	;	     EAX = Count down value (remain bytes)
  3371                              <1> 	;	
  3372                              <1> 	;	 For BH = 4 ; Get Current DMA channel (in progress)
  3373                              <1> 	;	     EAX = DMA channel number (0 to 7)
  3374                              <1> 	;		AH = 0 if the owner is the caller process
  3375                              <1> 	;		AH > 0 if the dma channel is in use by
  3376                              <1> 	;		       another user/process
  3377                              <1> 	;	     EAX = -1 (0FFFFFFFFh) 
  3378                              <1> 	;		    if DMA service is not in use	    		
  3379                              <1> 	;	 	    (stopped or not initialized/started)	
  3380                              <1> 	;
  3381                              <1> 	;	 For BH = 5 ; Get System's Default DMA Buff Addr
  3382                              <1> 	;	     EAX = Default DMA Buffer Address (Physical)
  3383                              <1> 	;		 = offset 'sb16_dma_buffer:'	
  3384                              <1> 	;	     ECX = Buffer size
  3385                              <1> 	;		 = 65536 
  3386                              <1> 	;
  3387                              <1> 	;	 For BH = 6 ; Get Current DMA Buffer Address
  3388                              <1> 	;	     EAX = Current DMA buffer address (Physical)
  3389                              <1> 	;	     ECX = Current DMA buffer size (setting value)	   		  	 		
  3390                              <1> 	;	     Note: These values are for current dma channel
  3391                              <1> 	;		   settings for the user/process
  3392                              <1> 	;	     ** For now (for current TRDOS 386 version)
  3393                              <1> 	;		only one user/process can use only one
  3394                              <1> 	;		dma channel & one dma buffer at same time
  3395                              <1> 	;		(no multi tasking on DMA service) !!! **
  3396                              <1> 	;	     (Once, current DMA user must stop it's own DMA
  3397                              <1> 	;	      DMA service, than another user/program 
  3398                              <1> 	;	      can use DMA service with same dma channel 
  3399                              <1> 	;	      or with another DMA channel.)	 			      		
  3400                              <1> 	;
  3401                              <1> 	;	 For BH = 7 ; Stop DMA service (for current user
  3402                              <1> 	;	     and current DMA channel)	
  3403                              <1> 	;	     EAX = 0 ; successful
  3404                              <1> 	;	     CF = 1 & EAX > 0 (= -1) -> Error		
  3405                              <1> 
  3406 00010F61 80FF07              <1> 	cmp	bh, 7
  3407 00010F64 7612                <1> 	jna	short sysdma_0
  3408                              <1> 
  3409                              <1> sysdma_err:
  3410 00010F66 31C0                <1> 	xor	eax, eax
  3411 00010F68 48                  <1> 	dec	eax ; -1
  3412                              <1> sysdma_perm_err:
  3413 00010F69 A3[64030300]        <1> 	mov	[u.r0], eax
  3414 00010F6E A3[C8030300]        <1> 	mov	[u.error], eax ; DMA service error !
  3415 00010F73 E902C0FFFF          <1> 	jmp	error
  3416                              <1> 
  3417                              <1> sysdma_0:
  3418 00010F78 08FF                <1> 	or	bh, bh
  3419 00010F7A 0F85BA000000        <1> 	jnz	sysdma_1
  3420                              <1> 	
  3421 00010F80 20DB                <1> 	and	bl, bl
  3422 00010F82 7416                <1> 	jz	short sysdma_01
  3423                              <1> 
  3424                              <1> 	; redirect system call to 'sysalloc'
  3425 00010F84 89D3                <1> 	mov	ebx, edx ; virtual address of DMA buffer
  3426                              <1> 	;ecx = Buffer size in bytes
  3427                              <1> 	; DMA buffer address <= 16MB upper limit
  3428 00010F86 BA00000001          <1> 	mov	edx, 1024*1024*16 ; 16MB limit for DMA buff
  3429                              <1> 
  3430 00010F8B C705[44750100]FFFF- <1> 	mov	dword [dma_addr], 0FFFFFFFFh ; -1
  3430 00010F93 FFFF                <1>
  3431                              <1> 
  3432 00010F95 E99DE5FFFF          <1> 	jmp	sysalloc
  3433                              <1> 
  3434                              <1> sysdma_01:
  3435 00010F9A B8[00000200]        <1> 	mov	eax, sb16_dma_buffer
  3436                              <1> 
  3437 00010F9F 803D[01710100]01    <1> 	cmp	byte [audio_device], 1
  3438 00010FA6 722A                <1> 	jb	short sysdma_03
  3439                              <1> 
  3440 00010FA8 3B05[20710100]      <1> 	cmp	eax, [audio_dma_buff]
  3441 00010FAE 7507                <1> 	jne	short sysdma_02
  3442                              <1> 
  3443                              <1> sysdma_0_err:
  3444 00010FB0 B80B000000          <1> 	mov	eax, ERR_PERM_DENIED
  3445 00010FB5 EBB2                <1> 	jmp	short sysdma_perm_err
  3446                              <1> 
  3447                              <1> sysdma_02:
  3448                              <1> 	; Only one user is permitted for audio/dma functions
  3449                              <1> 
  3450 00010FB7 833D[20710100]00    <1> 	cmp	dword [audio_dma_buff], 0
  3451 00010FBE 7612                <1> 	jna	short sysdma_03
  3452                              <1> 
  3453 00010FC0 8A1D[29710100]      <1> 	mov	bl, [audio_user]
  3454 00010FC6 08DB                <1> 	or	bl, bl
  3455 00010FC8 7408                <1> 	jz	short sysdma_03
  3456                              <1> 
  3457 00010FCA 3A1D[B3030300]      <1> 	cmp	bl, [u.uno]
  3458 00010FD0 75DE                <1> 	jne	short sysdma_0_err
  3459                              <1> 
  3460                              <1> sysdma_03: 
  3461 00010FD2 8A1D[41750100]      <1> 	mov	bl, [dma_user]
  3462 00010FD8 20DB                <1> 	and	bl, bl
  3463 00010FDA 750E                <1> 	jnz	short sysdma_04
  3464                              <1> 	
  3465 00010FDC 8A1D[B3030300]      <1> 	mov	bl, [u.uno]
  3466 00010FE2 881D[41750100]      <1> 	mov	[dma_user], bl
  3467                              <1> 
  3468 00010FE8 EB15                <1> 	jmp	short sysdma_05
  3469                              <1> 
  3470                              <1> sysdma_04:
  3471 00010FEA 8B35[44750100]      <1> 	mov	esi, [dma_addr]
  3472 00010FF0 21F6                <1> 	and	esi, esi
  3473 00010FF2 740B                <1> 	jz	short sysdma_05
  3474                              <1> 
  3475 00010FF4 46                  <1> 	inc	esi ; -1 -> 0
  3476 00010FF5 7408                <1> 	jz	short sysdma_05
  3477                              <1> 
  3478 00010FF7 3A1D[B3030300]      <1> 	cmp	bl, [u.uno]
  3479 00010FFD 75B1                <1> 	jne	short sysdma_0_err
  3480                              <1> 	
  3481                              <1> sysdma_05:
  3482                              <1> 	; edx = virtual address (user's buffer address)
  3483                              <1> 	; 
  3484 00010FFF 81F900000100        <1> 	cmp	ecx, 65536   ; byte count (buffer size)
  3485 00011005 0F875BFFFFFF        <1> 	ja	sysdma_err	
  3486                              <1> 	;
  3487 0001100B 81C1FF0F0000        <1> 	add	ecx, PAGE_SIZE-1 ; 4095
  3488 00011011 6681E100F0          <1> 	and	cx, ~PAGE_OFF ; not 4095
  3489                              <1> 	;cmp	ecx, 65536
  3490                              <1> 	;ja	sysdma_err ;
  3491 00011016 51                  <1> 	push	ecx	; buffer size (allocated pages * 4096) 
  3492 00011017 50                  <1> 	push	eax	; offset sb16_dma_buffer
  3493 00011018 89D3                <1> 	mov	ebx, edx
  3494 0001101A C1E90C              <1> 	shr	ecx, 12 ; byte count to page count
  3495                              <1> 	; eax = physical address of (audio) dma buffer
  3496                              <1> 	; ebx = virtual address of (audio) dma buffer (user's pgdir) 
  3497                              <1> 	; ecx = page count (>0)
  3498 0001101D E8EA4DFFFF          <1> 	call	direct_memory_access
  3499 00011022 58                  <1> 	pop	eax
  3500 00011023 59                  <1> 	pop	ecx
  3501 00011024 0F823CFFFFFF        <1> 	jc	sysdma_err
  3502                              <1> 
  3503 0001102A A3[44750100]        <1> 	mov	[dma_addr], eax
  3504 0001102F 890D[48750100]      <1> 	mov	[dma_size], ecx ; dma buffer size (in bytes)
  3505                              <1> 
  3506                              <1> 	;mov	[u.r0], eax ; DMA Buffer Address (Physical)
  3507                              <1> 
  3508                              <1> 	;mov	ebp, [u.usp]  ; ebp points to user's registers
  3509                              <1> 	;mov	[ebp+24], ecx ; return to user with ecx value
  3510                              <1> 
  3511                              <1> 	;jmp	sysret
  3512                              <1> 
  3513                              <1> 	; 28/08/2017
  3514 00011035 E9C4000000          <1> 	jmp	sysdma_51
  3515                              <1> 
  3516                              <1> sysdma_1:
  3517 0001103A 80FF01              <1> 	cmp	bh, 1
  3518 0001103D 0F87A6000000        <1> 	ja	sysdma_5
  3519                              <1> 
  3520 00011043 F6C340              <1> 	test	bl, 40h	; record (read) mode -BL, bit 6-
  3521 00011046 0F851AFFFFFF        <1> 	jnz	sysdma_err ; not ready yet!
  3522                              <1> 
  3523 0001104C A1[44750100]        <1> 	mov	eax, [dma_addr] ; physical address of dma buffer
  3524 00011051 21C0                <1> 	and	eax, eax
  3525 00011053 0F840DFFFFFF        <1> 	jz	sysdma_err
  3526                              <1> 
  3527 00011059 09D2                <1> 	or	edx, edx
  3528 0001105B 7504                <1> 	jnz	short sysdma_11
  3529                              <1> 
  3530 0001105D 89C2                <1> 	mov	edx, eax
  3531 0001105F EB08                <1> 	jmp	short sysdma_12	
  3532                              <1> sysdma_11:
  3533 00011061 39C2                <1> 	cmp	edx, eax
  3534 00011063 0F82FDFEFFFF        <1> 	jb	sysdma_err
  3535                              <1> sysdma_12:
  3536 00011069 21C9                <1> 	and	ecx, ecx
  3537 0001106B 7508                <1> 	jnz	short sysdma_13
  3538                              <1> 
  3539 0001106D 8B0D[48750100]      <1> 	mov	ecx, [dma_size]
  3540 00011073 EB0C                <1> 	jmp	short sysdma_14
  3541                              <1> sysdma_13:
  3542 00011075 3B0D[48750100]      <1> 	cmp	ecx, [dma_size]
  3543 0001107B 0F87E5FEFFFF        <1> 	ja	sysdma_err
  3544                              <1> sysdma_14:
  3545 00011081 89C6                <1> 	mov	esi, eax
  3546 00011083 0335[48750100]      <1> 	add	esi, [dma_size]
  3547                              <1> 
  3548 00011089 89D0                <1> 	mov	eax, edx
  3549 0001108B 01C8                <1> 	add	eax, ecx
  3550 0001108D 0F82D3FEFFFF        <1> 	jc	sysdma_err ; 02/09/2017	
  3551                              <1> 		
  3552 00011093 39F0                <1> 	cmp	eax, esi
  3553 00011095 0F87CBFEFFFF        <1> 	ja	sysdma_err
  3554                              <1> 
  3555 0001109B 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff]
  3556 000110A1 8B35[44750100]      <1> 	mov	esi, [dma_addr]
  3557                              <1> 
  3558 000110A7 09FF                <1> 	or	edi, edi
  3559 000110A9 7424                <1> 	jz	short sysdma_16
  3560                              <1> 	
  3561 000110AB 803D[01710100]01    <1> 	cmp	byte [audio_device], 1
  3562 000110B2 7208                <1> 	jb	short sysdma_15
  3563                              <1> 
  3564                              <1> 	; Sound Blaster 16
  3565 000110B4 39FE                <1> 	cmp	esi, edi
  3566 000110B6 0F84F4FEFFFF        <1> 	je	sysdma_0_err ; permmission denied !
  3567                              <1> 
  3568                              <1> sysdma_15:
  3569 000110BC C605[43750100]48    <1> 	mov	byte [dma_mode], 48h ; single mode playback	
  3570                              <1> 
  3571 000110C3 F6C380              <1> 	test	bl, 80h ; DMA mode - BL, bit 7, auto init -
  3572 000110C6 7407                <1> 	jz	short sysdma_16	
  3573                              <1> 	; Auto initialized playback (write) mode
  3574 000110C8 8005[43750100]10    <1> 	add	byte [dma_mode], 10h ; = 58h
  3575                              <1> sysdma_16:
  3576 000110CF 80E307              <1> 	and	bl, 07h
  3577 000110D2 881D[42750100]      <1> 	mov	[dma_channel], bl
  3578 000110D8 8915[4C750100]      <1> 	mov	[dma_start], edx
  3579 000110DE 890D[50750100]      <1> 	mov	[dma_count], ecx
  3580                              <1> 	 
  3581                              <1> 	; 28/08/2017
  3582                              <1> 	;call	dma_init
  3583                              <1> 	;jmp	sysret
  3584 000110E4 E94B010000          <1> 	jmp	dma_init
  3585                              <1> 
  3586                              <1> sysdma_5:
  3587 000110E9 80FF05              <1> 	cmp	bh, 5
  3588 000110EC 7223                <1> 	jb	short sysdma_3
  3589 000110EE 0F87CE000000        <1> 	ja	sysdma_6	
  3590                              <1> 
  3591                              <1> 	; Get the system's default dma buffer addr and size
  3592 000110F4 B8[00000200]        <1> 	mov	eax, sb16_dma_buffer
  3593 000110F9 B900000100          <1> 	mov	ecx, 65536 ; Buffer size in bytes
  3594                              <1> 
  3595                              <1> sysdma_51:
  3596                              <1> 	; 0 = there is not a dma buffer (in use or available)
  3597 000110FE A3[64030300]        <1> 	mov	[u.r0], eax
  3598                              <1> 
  3599 00011103 8B2D[60030300]      <1> 	mov	ebp, [u.usp]  ; ebp points to user's registers
  3600 00011109 894D18              <1> 	mov	[ebp+24], ecx ; return to user with ecx value
  3601                              <1> 
  3602 0001110C E989BEFFFF          <1> 	jmp	sysret
  3603                              <1> 
  3604                              <1> sysdma_3:
  3605 00011111 80FF03              <1> 	cmp	bh, 3
  3606 00011114 7231                <1> 	jb	short sysdma_2
  3607 00011116 776B                <1> 	ja	short sysdma_4
  3608                              <1> 
  3609                              <1> 	; Get current dma count down value (remain bytes)
  3610                              <1> 	; 28/08/2017
  3611 00011118 0FB635[42750100]    <1> 	movzx	esi, byte [dma_channel]
  3612 0001111F 0FB696[341C0100]    <1> 	movzx	edx, byte [dma_flip+esi]
  3613 00011126 EE                  <1> 	out	dx, al			; flip-flop clear
  3614 00011127 8A96[141C0100]      <1> 	mov	dl, [dma_cnt+esi] ; dma count register addr
  3615 0001112D EC                  <1> 	in	al, dx
  3616 0001112E 0FB6D8              <1> 	movzx	ebx, al	
  3617 00011131 EC                  <1> 	in	al, dx
  3618 00011132 88C7                <1> 	mov     bh, al
  3619                              <1> 	
  3620 00011134 6683FE04            <1> 	cmp	si, 4 ; channel number ?
  3621 00011138 7202                <1> 	jb	short sysdma_31 ; 8 bit dma channel
  3622                              <1> 
  3623 0001113A D1E3                <1> 	shl	ebx, 1	; word count to byte count
  3624                              <1> 
  3625                              <1> sysdma_31:
  3626 0001113C 891D[64030300]      <1> 	mov	[u.r0], ebx
  3627                              <1> 
  3628 00011142 E953BEFFFF          <1> 	jmp	sysret	
  3629                              <1> 
  3630                              <1> sysdma_2:
  3631                              <1> 	; Get current dma buffer offset (& page)
  3632                              <1> 	; 28/08/2017
  3633 00011147 0FB635[42750100]    <1> 	movzx	esi, byte [dma_channel]
  3634 0001114E 0FB696[341C0100]    <1> 	movzx	edx, byte [dma_flip+esi]
  3635 00011155 EE                  <1> 	out	dx, al			; flip-flop clear
  3636 00011156 8A96[0C1C0100]      <1> 	mov	dl, [dma_adr+esi]
  3637 0001115C EC                  <1> 	in	al, dx			; get dma position
  3638 0001115D 0FB6D8              <1> 	movzx	ebx, al
  3639 00011160 EC                  <1> 	in	al, dx			
  3640 00011161 88C7                <1> 	mov	bh, al
  3641                              <1> 
  3642 00011163 6683FE04            <1> 	cmp	si, 4 ; channel number ?
  3643 00011167 7202                <1> 	jb	short sysdma_21 ; 8 bit dma channel
  3644                              <1> 
  3645 00011169 D1E3                <1> 	shl	ebx, 1	; word offset to byte offset
  3646                              <1> 
  3647                              <1> sysdma_21:
  3648 0001116B 891D[64030300]      <1> 	mov	[u.r0], ebx
  3649                              <1> 
  3650 00011171 8A96[1C1C0100]      <1> 	mov	dl, [dma_page+esi]
  3651 00011177 EC                  <1> 	in	al, dx			; get dma page
  3652                              <1> 
  3653                              <1> 	;add	[u.ro+2], al
  3654 00011178 0805[66030300]      <1> 	or	[u.r0+2], al
  3655                              <1> 
  3656 0001117E E917BEFFFF          <1> 	jmp	sysret
  3657                              <1> 
  3658                              <1> sysdma_4:
  3659                              <1> 	; Get current DMA channel number
  3660                              <1> 	; 28/08/2017
  3661 00011183 8A25[41750100]      <1> 	mov	ah, [dma_user]
  3662 00011189 20E4                <1> 	and	ah, ah
  3663 0001118B 750F                <1> 	jnz	short sysdma_42
  3664                              <1> 
  3665                              <1> sysdma_41:	
  3666                              <1> 	; Not a valid dma channel (in use)
  3667 0001118D C705[64030300]FFFF- <1> 	mov	dword [u.r0], -1 ; 0FFFFFFFFh
  3667 00011195 FFFF                <1>
  3668 00011197 E9FEBDFFFF          <1> 	jmp	sysret
  3669                              <1> 
  3670                              <1> sysdma_42:
  3671 0001119C 8B35[44750100]      <1> 	mov	esi, [dma_addr]
  3672 000111A2 21F6                <1> 	and	esi, esi
  3673 000111A4 74E7                <1> 	jz	short sysdma_41
  3674                              <1> 
  3675 000111A6 46                  <1> 	inc	esi ; -1 -> 0
  3676 000111A7 74E4                <1> 	jz	short sysdma_41
  3677                              <1> 
  3678 000111A9 A0[42750100]        <1> 	mov	al, [dma_channel]
  3679                              <1> 
  3680 000111AE 3A25[B3030300]      <1> 	cmp	ah, [u.uno]
  3681 000111B4 7502                <1> 	jne	short sysdma_43
  3682                              <1> 
  3683 000111B6 30E4                <1> 	xor	ah, ah ; DMA channel in use by current user
  3684                              <1> 
  3685                              <1> sysdma_43:
  3686 000111B8 A3[64030300]        <1> 	mov	[u.r0], eax ; AL = dma channel number
  3687                              <1> 			    ; AH > 0 if the the channel
  3688                              <1> 			    ; in use by another user/process
  3689 000111BD E9D8BDFFFF          <1> 	jmp	sysret
  3690                              <1> 
  3691                              <1> sysdma_6:
  3692 000111C2 80FF06              <1> 	cmp	bh, 6
  3693 000111C5 7710                <1> 	ja	short sysdma_7
  3694                              <1> 
  3695                              <1> 	; 28/08/2017
  3696                              <1> 	; Get current DMA buffer addr and size
  3697 000111C7 A1[44750100]        <1> 	mov	eax, [dma_addr] ; dma buffer address
  3698 000111CC 8B0D[48750100]      <1> 	mov	ecx, [dma_size] ; dma buffer size (in bytes)
  3699                              <1> 
  3700 000111D2 E927FFFFFF          <1> 	jmp	sysdma_51
  3701                              <1> 
  3702                              <1> sysdma_7:
  3703                              <1> 	; DMA service STOP
  3704 000111D7 A0[B3030300]        <1> 	mov	al, [u.uno]
  3705 000111DC 3A05[41750100]      <1> 	cmp	al, [dma_user]
  3706 000111E2 751D                <1> 	jne	short sysdma_72
  3707                              <1> 	
  3708 000111E4 28C0                <1> 	sub	al, al ; 0
  3709                              <1> 
  3710 000111E6 A2[41750100]        <1> 	mov	[dma_user], al ; clear user
  3711                              <1> 
  3712 000111EB 8605[43750100]      <1> 	xchg	al, [dma_mode]
  3713 000111F1 20C0                <1> 	and	al, al
  3714                              <1> 	;jz	short sysdma_err
  3715 000111F3 7527                <1> 	jnz	short sysdma_73	
  3716                              <1> 
  3717                              <1> sysdma_71:
  3718 000111F5 31C0                <1> 	xor	eax, eax
  3719 000111F7 A3[64030300]        <1> 	mov	[u.r0], eax; 0
  3720 000111FC E999BDFFFF          <1> 	jmp	sysret
  3721                              <1> 
  3722                              <1> sysdma_72:
  3723                              <1> 	; 28/08/2017
  3724 00011201 803D[41750100]00    <1> 	cmp	byte [dma_user], 0
  3725 00011208 76EB                <1> 	jna	short sysdma_71 ; Nothing to do !
  3726                              <1> 
  3727 0001120A 833D[44750100]00    <1> 	cmp	dword [dma_addr], 0
  3728 00011211 0F8799FDFFFF        <1> 	ja	sysdma_0_err
  3729                              <1> 	
  3730 00011217 A2[41750100]        <1> 	mov	[dma_user], al ; reset to current user
  3731                              <1> 
  3732                              <1> sysdma_73:
  3733                              <1> 	; 28/08/2017
  3734 0001121C 0FB635[42750100]    <1> 	movzx	esi, byte [dma_channel]
  3735 00011223 0FB696[241C0100]    <1> 	movzx	edx, byte [dma_mask+esi]
  3736 0001122A A0[42750100]        <1> 	mov	al, [dma_channel]
  3737 0001122F 0C04                <1> 	or	al, 4
  3738 00011231 EE                  <1> 	out	dx, al
  3739                              <1> 
  3740 00011232 EBC1                <1> 	jmp	short sysdma_71
  3741                              <1> 
  3742                              <1> dma_init:
  3743                              <1> 	; 28/08/2017
  3744                              <1> 	; 20/08/2017
  3745                              <1> 	; DMA initialization
  3746                              <1> 	; 14/08/2017
  3747                              <1> 	; 03/08/2017, 06/08/2017, 08/08/2017
  3748                              <1> 	; 02/07/2017, 13/07/2017, 16/07/2017, 30/07/2017
  3749                              <1> 	; (Derived from 'DMA_INIT' procedure in SB16MOD.ASM)
  3750                              <1> 	; Modified for TRDOS 386 DMA buffer allocation & initialization !
  3751                              <1> 
  3752 00011234 8B1D[4C750100]      <1> 	mov	ebx, [dma_start]
  3753 0001123A 8B0D[50750100]      <1> 	mov	ecx, [dma_count]
  3754                              <1> 
  3755 00011240 0FB635[42750100]    <1> 	movzx	esi, byte [dma_channel]
  3756                              <1> 
  3757 00011247 6683FE04            <1> 	cmp	si, 4
  3758 0001124B 7205                <1> 	jb	short gdmi1
  3759                              <1> 	; 08/08/2017
  3760 0001124D 66D1E9              <1> 	shr	cx, 1 ; word count
  3761 00011250 D1EB                <1> 	shr	ebx, 1 ; convert byte offset to word offset
  3762                              <1> gdmi1:
  3763                              <1> 	;mov	[dma_poff], bx ; 08/08/2017
  3764 00011252 6649                <1> 	dec	cx			; dma size = block size - 1
  3765                              <1> 	
  3766 00011254 0FB696[241C0100]    <1> 	movzx	edx, byte [dma_mask+esi] ; 30/07/2017
  3767 0001125B A0[42750100]        <1> 	mov	al, [dma_channel]
  3768 00011260 0C04                <1> 	or	al, 4
  3769 00011262 EE                  <1> 	out	dx, al			; dma channel mask
  3770                              <1> 
  3771 00011263 30C0                <1> 	xor	al, al ; 0 ; any value ! 08/08/2017
  3772 00011265 8A96[341C0100]      <1> 	mov	dl, [dma_flip+esi]
  3773 0001126B EE                  <1> 	out	dx, al			; flip-flop clear
  3774                              <1> 	
  3775 0001126C 8A96[2C1C0100]      <1> 	mov	dl, [dma_mod+esi]
  3776 00011272 A0[42750100]        <1> 	mov	al, [dma_channel]  ; 13/07/2017
  3777 00011277 2403                <1> 	and	al, 3
  3778                              <1> 	; 08/08/2017
  3779 00011279 0A05[43750100]      <1> 	or	al, [dma_mode] ; 58h    ; dma mode for SB16
  3780 0001127F EE                  <1> 	out	dx, al			
  3781                              <1> 
  3782 00011280 8A96[0C1C0100]      <1> 	mov	dl, [dma_adr+esi]	
  3783 00011286 88D8                <1> 	mov	al, bl			
  3784 00011288 EE                  <1> 	out	dx, al			; offset low
  3785                              <1> 
  3786 00011289 88F8                <1> 	mov	al, bh
  3787 0001128B EE                  <1> 	out	dx, al			; offset high
  3788                              <1> 
  3789 0001128C 8A96[141C0100]      <1> 	mov	dl, [dma_cnt+esi]
  3790 00011292 88C8                <1> 	mov	al, cl
  3791 00011294 EE                  <1> 	out	dx, al			; size low
  3792                              <1> 
  3793 00011295 88E8                <1> 	mov	al, ch
  3794 00011297 EE                  <1> 	out	dx, al			; size high
  3795                              <1> 
  3796 00011298 8A96[1C1C0100]      <1> 	mov	dl, [dma_page+esi]
  3797                              <1> 	; 14/08/2017 
  3798 0001129E 6683FE04            <1> 	cmp	si, 4
  3799 000112A2 7305                <1> 	jnb	short gdmi2
  3800 000112A4 C1EB10              <1> 	shr	ebx, 16
  3801 000112A7 EB06                <1> 	jmp	short gdmi3
  3802                              <1> gdmi2:
  3803                              <1> 	; 09/08/2017
  3804 000112A9 C1EB0F              <1> 	shr	ebx, 15	 ; complete 16 bit shift
  3805 000112AC 80E3FE              <1> 	and	bl, 0FEh ; clear bit 0 (not necessary)
  3806                              <1> gdmi3:	
  3807 000112AF 88D8                <1> 	mov	al, bl
  3808 000112B1 EE                  <1> 	out	dx, al			; page			
  3809                              <1> 	
  3810 000112B2 8A96[241C0100]      <1> 	mov	dl, [dma_mask+esi]
  3811 000112B8 A0[42750100]        <1> 	mov	al, [dma_channel]  ; 13/07/2017
  3812 000112BD 2403                <1> 	and	al, 3
  3813 000112BF EE                  <1> 	out	dx, al			; dma channel unmask
  3814                              <1> 
  3815                              <1> 	;retn
  3816                              <1> 	; 28/08/2017
  3817 000112C0 E9D5BCFFFF          <1> 	jmp	sysret
  3818                              <1> 
  3819                              <1> otty:
  3820                              <1> sret:
  3821                              <1> ocvt:
  3822                              <1> ctty:
  3823                              <1> cret:
  3824                              <1> ccvt:
  3825                              <1> rtty:
  3826                              <1> wtty:
  3827                              <1> rmem:
  3828                              <1> wmem:
  3829                              <1> rfd:
  3830                              <1> rhd:
  3831                              <1> wfd:
  3832                              <1> whd:
  3833                              <1> rlpt:
  3834                              <1> wlpt:
  3835                              <1> rcvt:
  3836                              <1> xmtt:
  3837 000112C5 C3                  <1> 	retn
  2869                                  %include 'trdosk9.s' ; 04/01/2016
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.3) - INITIALIZED DATA : trdosk9.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 30/11/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 04/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; ----------------------------------------------------------------------------
     9                              <1> ; Assembler: NASM version 2.15 (trdos386.s)
    10                              <1> ; ----------------------------------------------------------------------------
    11                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    12                              <1> ; TRDOS2.ASM (09/11/2011)
    13                              <1> ; ****************************************************************************
    14                              <1> ; DRV_INIT.ASM [26/09/2009] Last Update: 07/08/2011
    15                              <1> ; MAINPROG.ASM [17/01/2004] Last Update: 09/11/2011
    16                              <1> ; CMD_INTR.ASM [29/01/2005] Last Update: 09/11/2011
    17                              <1> ; FILE.ASM [29/10/2009] Last Update: 09/10/2011
    18                              <1> 
    19                              <1> ; 12/02/2016
    20                              <1> Last_DOS_DiskNo: 
    21 000112C6 01                  <1> 		db 1 ; A: = 0 & B: = 1
    22                              <1> 
    23                              <1> Restore_CDIR:	
    24 000112C7 FF                  <1> 		db 0FFh ; Initial value -> any number except 0
    25                              <1> 
    26                              <1> msg_CRLF_temp:  
    27 000112C8 070D0A00            <1> 		db 07h, 0Dh, 0Ah, 0
    28                              <1> 
    29                              <1> Magic_Bytes:
    30 000112CC 04                  <1> 		db 4
    31 000112CD 01                  <1> 		db 1
    32                              <1> mainprog_Version:
    33 000112CE 07                  <1> 		db 7
    34 000112CF 5B5452444F535D204D- <1> 		db "[TRDOS] Main Program v2.0.301120"
    34 000112D8 61696E2050726F6772- <1>
    34 000112E1 616D2076322E302E33- <1>
    34 000112EA 3031313230          <1>
    35 000112EF 0D0A                <1> 		db 0Dh, 0Ah
    36 000112F1 286329204572646F67- <1> 		db "(c) Erdogan Tan 2005-2020"
    36 000112FA 616E2054616E203230- <1>
    36 00011303 30352D32303230      <1>
    37 0001130A 0D0A00              <1> 		db 0Dh, 0Ah, 0
    38                              <1> 
    39                              <1> MainProgCfgFile: ; 14/04/2016
    40 0001130D 4D41494E50524F472E- <1> 		db "MAINPROG.CFG", 0
    40 00011316 43464700            <1>
    41                              <1> 
    42                              <1> TRDOSPromptLabel:
    43 0001131A 5452444F53          <1> 		db "TRDOS"
    44 0001131F 00                  <1> 		db 0
    45 00011320 00<rept>            <1>                 times 5 db 0
    46 00011325 00                  <1> 		db 0
    47                              <1> 
    48                              <1> ; INTERNAL COMMANDS
    49                              <1> Command_List:
    50 00011326 44495200            <1> Cmd_Dir:	db "DIR", 0
    51 0001132A 434400              <1> Cmd_Cd:		db "CD", 0
    52 0001132D 433A00              <1> Cmd_Drive:	db "C:", 0
    53 00011330 56455200            <1> Cmd_Ver:	db "VER", 0
    54 00011334 4558495400          <1> Cmd_Exit:	db "EXIT", 0
    55 00011339 50524F4D505400      <1> Cmd_Prompt:	db "PROMPT", 0
    56 00011340 564F4C554D4500      <1> Cmd_Volume:	db "VOLUME", 0
    57 00011347 4C4F4E474E414D4500  <1> Cmd_LongName:	db "LONGNAME", 0
    58 00011350 4441544500          <1> Cmd_Date:	db "DATE", 0
    59 00011355 54494D4500          <1> Cmd_Time:	db "TIME", 0
    60 0001135A 52554E00            <1> Cmd_Run:	db "RUN", 0
    61 0001135E 53455400            <1> Cmd_Set:	db "SET", 0 
    62 00011362 434C5300            <1> Cmd_Cls:	db "CLS", 0
    63 00011366 53484F5700          <1> Cmd_Show:	db "SHOW", 0
    64 0001136B 44454C00            <1> Cmd_Del:	db "DEL", 0
    65 0001136F 41545452494200      <1> Cmd_Attrib:	db "ATTRIB", 0
    66 00011376 52454E414D4500      <1> Cmd_Rename:	db "RENAME", 0
    67 0001137D 524D44495200        <1> Cmd_Rmdir:	db "RMDIR", 0
    68 00011383 4D4B44495200        <1> Cmd_Mkdir:	db "MKDIR", 0
    69 00011389 434F505900          <1> Cmd_Copy:	db "COPY", 0
    70 0001138E 4D4F564500          <1> Cmd_Move:	db "MOVE", 0
    71 00011393 5041544800          <1> Cmd_Path:	db "PATH", 0
    72 00011398 4D454D00            <1> Cmd_Mem:	db "MEM", 0
    73 0001139C 00                  <1> 		db 0
    74 0001139D 46494E4400          <1> Cmd_Find:	db "FIND", 0
    75 000113A2 4543484F00          <1> Cmd_Echo:	db "ECHO", 0
    76 000113A7 2A00                <1> Cmd_Remark:	db "*", 0
    77 000113A9 3F00                <1> Cmd_Help:	db "?", 0
    78 000113AB 44455649434500      <1> Cmd_Device:	db "DEVICE", 0
    79 000113B2 4445564C49535400    <1> Cmd_DevList:	db "DEVLIST", 0
    80 000113BA 434844495200        <1> Cmd_Chdir:	db "CHDIR", 0
    81 000113C0 4245455000          <1> Cmd_Beep:	db "BEEP", 0
    82                              <1> 		
    83 000113C5 00                  <1> 		db 0
    84                              <1> 
    85                              <1> ; 15/02/2016 (FILE.ASM, 09/10/2011)
    86                              <1> invalid_fname_chars:
    87 000113C6 222728292A2B2C2F    <1> 		db 22h, 27h, 28h, 29h, 2Ah, 2Bh, 2Ch, 2Fh
    88 000113CE 3A3B3C3D3E3F40      <1> 		db 3Ah, 3Bh, 3Ch, 3Dh, 3Eh, 3Fh, 40h
    89 000113D5 5B5C5D5E60          <1> 		db 5Bh, 5Ch, 5Dh, 5Eh, 60h
    90                              <1> sizeInvFnChars  equ ($ - invalid_fname_chars)                
    91                              <1> ;
    92                              <1> 
    93                              <1> Msg_Enter_Date:
    94 000113DA 456E746572206E6577- <1>                 db 'Enter new date (dd-mm-yy): '
    94 000113E3 206461746520286464- <1>
    94 000113EC 2D6D6D2D7979293A20  <1>
    95 000113F5 00                  <1>                 db 0
    96                              <1> Msg_Show_Date:
    97 000113F6 43757272656E742064- <1>                 db   'Current date is '
    97 000113FF 61746520697320      <1>
    98 00011406 30                  <1> Day:            db   '0'
    99 00011407 30                  <1> 		db   '0'
   100 00011408 2F                  <1>                 db   '/'
   101 00011409 30                  <1> Month:          db   '0'
   102 0001140A 30                  <1> 		db   '0'
   103 0001140B 2F                  <1>                 db   '/'
   104 0001140C 30                  <1> Century:        db   '0'
   105 0001140D 30                  <1>                 db   '0'
   106 0001140E 30                  <1> Year:           db   '0'
   107 0001140F 30                  <1> 		db   '0'
   108 00011410 0D0A00              <1>                 db   0Dh, 0Ah, 0
   109                              <1> 
   110                              <1> Msg_Enter_Time:
   111 00011413 456E746572206E6577- <1> 		db 'Enter new time: '
   111 0001141C 2074696D653A20      <1>
   112 00011423 00                  <1> 		db 0
   113                              <1> Msg_Show_Time:
   114 00011424 43757272656E742074- <1> 		db   'Current time is '
   114 0001142D 696D6520697320      <1>
   115 00011434 30                  <1> Hour:           db   '0'
   116 00011435 30                  <1> 		db   '0'
   117 00011436 3A                  <1> 		db   ':'
   118 00011437 30                  <1> Minute:         db   '0'
   119 00011438 30                  <1> 		db   '0'
   120 00011439 3A                  <1> 		db   ':'
   121 0001143A 30                  <1> Second:         db   '0'
   122 0001143B 30                  <1> 		db   '0'
   123 0001143C 0D0A00              <1> 		db   0Dh, 0Ah, 0
   124                              <1> 
   125                              <1> ;VolSize_Unit1:   dd 0
   126                              <1> ;VolSize_Unit2:   dd 0
   127                              <1> 
   128                              <1> VolSize_KiloBytes:
   129 0001143F 206B696C6F62797465- <1> 		db " kilobytes", 0Dh, 0Ah, 0
   129 00011448 730D0A00            <1>
   130                              <1> VolSize_Bytes:
   131 0001144C 2062797465730D0A00  <1> 		db " bytes", 0Dh, 0Ah, 0
   132                              <1> Volume_in_drive:
   133 00011455 0D0A                <1> 		db 0Dh, 0Ah
   134                              <1> Vol_FS_Name:
   135 00011457 54522046533120      <1> 		db "TR FS1 "
   136 0001145E 566F6C756D6520696E- <1> 		db "Volume in drive "
   136 00011467 20647269766520      <1>
   137 0001146E 30                  <1> Vol_Drv_Name:   db 30h
   138 0001146F 3A                  <1> 		db ":"
   139 00011470 20697320            <1> 		db " is "
   140 00011474 0D0A00              <1> 		db 0Dh, 0Ah, 0
   141                              <1> Dir_Drive_Str:
   142 00011477 54522D444F53204472- <1>                 db "TR-DOS Drive "
   142 00011480 69766520            <1>
   143                              <1> Dir_Drive_Name:
   144 00011484 303A                <1>                 db "0:"
   145 00011486 0D0A                <1>                 db  0Dh, 0Ah
   146                              <1> Vol_Str_Header:
   147 00011488 566F6C756D65204E61- <1>                 db "Volume Name: "
   147 00011491 6D653A20            <1>
   148                              <1> Vol_Name:
   149 00011495 00<rept>            <1> 		times 64 db 0
   150 000114D5 00                  <1> 		db 0
   151                              <1> Vol_Serial_Header:
   152 000114D6 0D0A                <1> 		db 0Dh, 0Ah
   153 000114D8 566F6C756D65205365- <1> 		db "Volume Serial No: "
   153 000114E1 7269616C204E6F3A20  <1>
   154                              <1> Vol_Serial1:
   155 000114EA 30303030            <1> 		db "0000"
   156 000114EE 2D                  <1> 		db "-"
   157                              <1> Vol_Serial2:
   158 000114EF 30303030            <1> 		db "0000"
   159 000114F3 0D0A00              <1> 		db 0Dh, 0Ah, 0
   160                              <1> 
   161                              <1> ;Vol_Tot_Sec_Str_Start:
   162                              <1> ;		dd 0
   163                              <1> Vol_Total_Sector_Header:
   164 000114F6 0D0A                <1> 		db 0Dh, 0Ah
   165 000114F8 566F6C756D65205369- <1> 		db "Volume Size : ", 0
   165 00011501 7A65203A2000        <1>
   166                              <1> ;Vol_Tot_Sec_Str: 
   167                              <1> ;		db "0000000000"
   168                              <1> ;Vol_Tot_Sec_Str_End:
   169                              <1> ;		db 0
   170                              <1> ;Vol_Free_Sectors_Str_Start:
   171                              <1> ;		dd 0
   172                              <1> Vol_Free_Sectors_Header:
   173 00011507 467265652053706163- <1> 		db "Free Space  : ", 0
   173 00011510 6520203A2000        <1>
   174                              <1> ;Vol_Free_Sectors_Str:
   175                              <1> ;		db "0000000000"
   176                              <1> ;Vol_Free_Sectors_Str_End:
   177                              <1> ;		db 0
   178                              <1> 
   179                              <1> Dir_Str_Header:
   180 00011516 4469726563746F7279- <1>                 db "Directory: "
   180 0001151F 3A20                <1>
   181 00011521 2F                  <1> Dir_Str_Root:   db "/"
   182 00011522 00<rept>            <1> Dir_Str:        times 64 db 0
   183 00011562 00000000            <1>                 dd 0
   184 00011566 00                  <1>                 db 0
   185                              <1> 
   186                              <1> Msg_Bad_Command:
   187 00011567 42616420636F6D6D61- <1>                 db "Bad command or file name!"
   187 00011570 6E64206F722066696C- <1>
   187 00011579 65206E616D6521      <1>
   188 00011580 0D0A00              <1>                 db 0Dh, 0Ah, 0
   189                              <1> 
   190                              <1> msgl_drv_not_ready: 
   191 00011583 070D0A              <1> 		db 07h, 0Dh, 0Ah
   192                              <1> 
   193                              <1> ; CMD_INTR.ASM - 09/11/2011 - Messages
   194                              <1> 
   195                              <1> Msg_Not_Ready_Read_Err:
   196 00011586 4472697665206E6F74- <1>                 db "Drive not ready or read error!"
   196 0001158F 207265616479206F72- <1>
   196 00011598 207265616420657272- <1>
   196 000115A1 6F7221              <1>
   197 000115A4 0D0A00              <1>                 db 0Dh, 0Ah, 0
   198                              <1> 
   199                              <1> Msg_Not_Ready_Write_Err:
   200 000115A7 4472697665206E6F74- <1>                 db "Drive not ready or write error!"
   200 000115B0 207265616479206F72- <1>
   200 000115B9 207772697465206572- <1>
   200 000115C2 726F7221            <1>
   201 000115C6 0D0A00              <1>                 db 0Dh, 0Ah, 0
   202                              <1> 
   203                              <1> Msg_Dir_Not_Found:
   204 000115C9 4469726563746F7279- <1>                 db "Directory not found!"
   204 000115D2 206E6F7420666F756E- <1>
   204 000115DB 6421                <1>
   205 000115DD 0D0A00              <1>                 db 0Dh, 0Ah, 0
   206                              <1> 
   207                              <1> Msg_File_Not_Found:
   208 000115E0 46696C65206E6F7420- <1>                 db "File not found!"
   208 000115E9 666F756E6421        <1>
   209 000115EF 0D0A00              <1>                 db 0Dh, 0Ah, 0
   210                              <1> 
   211                              <1> Msg_File_Directory_Not_Found:
   212 000115F2 46696C65206F722064- <1>                 db "File or directory not found!"
   212 000115FB 69726563746F727920- <1>
   212 00011604 6E6F7420666F756E64- <1>
   212 0001160D 21                  <1>
   213 0001160E 0D0A00              <1>                 db 0Dh, 0Ah, 0
   214                              <1> 
   215                              <1> Msg_LongName_Not_Found:
   216 00011611 4C6F6E67206E616D65- <1>                 db "Long name not found!"
   216 0001161A 206E6F7420666F756E- <1>
   216 00011623 6421                <1>
   217 00011625 0D0A00              <1>                 db 0Dh, 0Ah, 0
   218                              <1> 
   219                              <1> beep_Insufficient_Memory: ; 20/02/2017
   220 00011628 0D0A                <1> 		db 0Dh, 0Ah
   221 0001162A 07                  <1> 		db 07h
   222                              <1> Msg_Insufficient_Memory:
   223 0001162B 496E73756666696369- <1>                 db "Insufficient memory!"
   223 00011634 656E74206D656D6F72- <1>
   223 0001163D 7921                <1>
   224 0001163F 0D0A00              <1>                 db 0Dh, 0Ah, 0
   225                              <1> 
   226                              <1> Msg_Error_Code:
   227 00011642 436F6D6D616E642066- <1>                 db 'Command failed! Error code : '
   227 0001164B 61696C656421204572- <1>
   227 00011654 726F7220636F646520- <1>
   227 0001165D 3A20                <1>
   228 0001165F 303068              <1> error_code_hex: db '00h'
   229 00011662 0A0A00              <1>                 db 0Ah, 0Ah, 0
   230                              <1> 
   231 00011665 90                  <1> align 2
   232                              <1> 
   233                              <1> ; 10/02/2016
   234                              <1> ; DIR.ASM - 09/10/2011
   235                              <1> 
   236 00011666 3C4449523E20202020- <1> Type_Dir:       db '<DIR>     ' ; 10 bytes
   236 0001166F 20                  <1>
   237                              <1> 
   238                              <1> File_Name:
   239 00011670 20<rept>            <1>                 times 12 db 20h
   240 0001167C 20                  <1> 		db 20h
   241                              <1> Dir_Or_FileSize:
   242 0001167D 20<rept>            <1>                 times 10 db 20h
   243 00011687 20                  <1> 		db 20h
   244                              <1> File_Attribute:
   245 00011688 20202020            <1> 		dd 20202020h
   246 0001168C 20                  <1> 		db 20h
   247                              <1> File_Day:
   248 0001168D 3030                <1>                 db '0','0'
   249 0001168F 2F                  <1> 		db '/'
   250                              <1> File_Month:
   251 00011690 3030                <1>                 db '0','0'
   252 00011692 2F                  <1> 		db '/'
   253                              <1> File_Year:
   254 00011693 30303030            <1>                 db '0','0','0','0'
   255 00011697 20                  <1> 		db 20h
   256                              <1> File_Hour:
   257 00011698 3030                <1>                 db '0','0'
   258 0001169A 3A                  <1> 		db ':'
   259                              <1> File_Minute:
   260 0001169B 3030                <1>                 db '0','0'
   261 0001169D 00                  <1> 		db 0
   262                              <1> 
   263                              <1> Decimal_File_Count_Header:
   264 0001169E 0D0A                <1> 		db 0Dh, 0Ah
   265                              <1> Decimal_File_Count:
   266 000116A0 00<rept>            <1> 		times 6 db 0
   267                              <1> 
   268 000116A6 2066696C6528732920- <1> str_files:	db " file(s) & "
   268 000116AF 2620                <1>
   269                              <1> Decimal_Dir_Count: 
   270 000116B1 00<rept>            <1> 		times 6 db 0
   271                              <1> str_dirs:       
   272 000116B7 206469726563746F72- <1> 		db " directory(s) "
   272 000116C0 7928732920          <1>
   273 000116C5 0D0A00              <1> 		db 0Dh, 0Ah, 0
   274                              <1> 
   275 000116C8 206279746528732920- <1> str_bytes:	db " byte(s) in file(s)"
   275 000116D1 696E2066696C652873- <1>
   275 000116DA 29                  <1>
   276 000116DB 0D0A00              <1> 		db 0Dh, 0Ah, 0
   277                              <1> 
   278                              <1> ; CMD_INTR.ASM - 09/11/2011
   279                              <1> ; 07/10/2010
   280                              <1> Msg_invalid_name_chars:
   281 000116DE 496E76616C69642066- <1>                 db "Invalid file or directory name characters!"
   281 000116E7 696C65206F72206469- <1>
   281 000116F0 726563746F7279206E- <1>
   281 000116F9 616D65206368617261- <1>
   281 00011702 637465727321        <1>
   282 00011708 0D0A00              <1>         	db 0Dh, 0Ah, 0
   283                              <1> ; 21/02/2016
   284 0001170B 46696C65206F722064- <1> Msg_Name_Exists: db "File or directory name exists!"
   284 00011714 69726563746F727920- <1>
   284 0001171D 6E616D652065786973- <1>
   284 00011726 747321              <1>
   285 00011729 0D0A00              <1>                 db 0Dh, 0Ah, 0
   286                              <1> Msg_DoYouWantMkdir:
   287 0001172C 446F20796F75207761- <1>                 db "Do you want to make directory ", 0
   287 00011735 6E7420746F206D616B- <1>
   287 0001173E 65206469726563746F- <1>
   287 00011747 72792000            <1>
   288 0001174B 2028592F4E29203F20- <1> Msg_YesNo:      db " (Y/N) ? ", 0  
   288 00011754 00                  <1>
   289 00011755 000D0A00            <1> Y_N_nextline:	db 0, 0Dh, 0Ah, 0 
   290 00011759 4F4B2E0D0A00        <1> Msg_OK:		db "OK.", 0Dh, 0Ah, 0
   291                              <1> 
   292                              <1> ; 27/02/2016
   293                              <1> Msg_DoYouWantRmDir:
   294 0001175F 446F20796F75207761- <1>                 db "Do you want to delete directory ", 0
   294 00011768 6E7420746F2064656C- <1>
   294 00011771 657465206469726563- <1>
   294 0001177A 746F72792000        <1>
   295                              <1> Msg_Dir_Not_Empty:
   296 00011780 4469726563746F7279- <1>                 db "Directory not empty!"
   296 00011789 206E6F7420656D7074- <1>
   296 00011792 7921                <1>
   297 00011794 0D0A00              <1>                 db 0Dh, 0Ah, 0
   298                              <1> 
   299                              <1> Msg_DoYouWantDelete:
   300 00011797 446F20796F75207761- <1>                 db "Do you want to delete file ",0
   300 000117A0 6E7420746F2064656C- <1>
   300 000117A9 6574652066696C6520- <1>
   300 000117B2 00                  <1>
   301                              <1> 
   302 000117B3 44656C657465642E2E- <1> Msg_Deleted:    db "Deleted...", 0Dh, 0Ah, 0
   302 000117BC 2E0D0A00            <1>
   303                              <1> 
   304                              <1> Msg_Permission_Denied:
   305 000117C0 07                  <1>                 db 7
   306 000117C1 5065726D697373696F- <1>                 db "Permission denied!", 0Dh, 0Ah, 0
   306 000117CA 6E2064656E69656421- <1>
   306 000117D3 0D0A00              <1>
   307                              <1> 
   308                              <1> ; 04/03/2016
   309 000117D6 4E657720            <1> Msg_New:        db "New "
   310 000117DA 00                  <1>                 db 0
   311                              <1> Str_Attributes:
   312 000117DB 417474726962757465- <1>                 db "Attributes : "
   312 000117E4 73203A20            <1>
   313 000117E8 4E4F524D414C        <1> Attr_Chars:     db "NORMAL"
   314 000117EE 00                  <1>                 db 0
   315                              <1> 
   316                              <1> ; 06/03/2016
   317                              <1> ; CMD_INTR.ASM - 16/11/2010 
   318                              <1> Msg_DoYouWantRename:
   319 000117EF 446F20796F75207761- <1>                 db "Do you want to rename ", 0
   319 000117F8 6E7420746F2072656E- <1>
   319 00011801 616D652000          <1>
   320 00011806 66696C652000        <1> Rename_File:    db "file ", 0
   321 0001180C 6469726563746F7279- <1> Rename_Directory: db "directory ", 0
   321 00011815 2000                <1>
   322 00011817 00<rept>            <1> Rename_OldName: times 13 db 0
   323 00011824 20617320            <1> Msg_File_rename_as: db " as "
   324 00011828 00<rept>            <1> Rename_NewName: times 13 db 0
   325                              <1> 
   326                              <1> ; 08/03/2016
   327                              <1> ; CMD_INTR.ASM - 01/08/2010 - 23/04/2011
   328                              <1> msg_not_same_drv:
   329 00011835 4E6F742073616D6520- <1>                 db "Not same drive!" 
   329 0001183E 647269766521        <1>
   330 00011844 0D0A00              <1>                 db 0Dh, 0Ah, 0 
   331                              <1> 
   332                              <1> Msg_DoYouWantMoveFile:
   333 00011847 446F20796F75207761- <1>                 db "Do you want to move file", 0
   333 00011850 6E7420746F206D6F76- <1>
   333 00011859 652066696C6500      <1>
   334                              <1> 
   335                              <1> msg_insufficient_disk_space:
   336 00011860 496E73756666696369- <1>                 db "Insufficient disk space!" 
   336 00011869 656E74206469736B20- <1>
   336 00011872 737061636521        <1>
   337 00011878 0D0A00              <1>                 db 0Dh, 0Ah, 0
   338                              <1> 
   339                              <1> ; 01/08/2010
   340                              <1> msg_source_file: 
   341 0001187B 0D0A536F7572636520- <1> 		db 0Dh, 0Ah, "Source file name      :   "
   341 00011884 66696C65206E616D65- <1>
   341 0001188D 2020202020203A2020- <1>
   341 00011896 20                  <1>
   342                              <1> msg_source_file_drv: 
   343 00011897 203A00              <1> 		db " :", 0
   344                              <1> msg_destination_file: 
   345 0001189A 0D0A44657374696E61- <1> 		db 0Dh, 0Ah, "Destination file name :   "
   345 000118A3 74696F6E2066696C65- <1>
   345 000118AC 206E616D65203A2020- <1>
   345 000118B5 20                  <1>
   346                              <1> msg_destination_file_drv: 
   347 000118B6 203A00              <1> 		db " :", 0
   348                              <1> msg_copy_nextline: 
   349 000118B9 0D0A00              <1> 		db 0Dh, 0Ah, 0
   350                              <1> 
   351                              <1> ; 15/03/2016
   352                              <1> ; CMD_INTR.ASM
   353                              <1> 
   354                              <1> Msg_DoYouWantOverWriteFile:
   355 000118BC 446F20796F75207761- <1>                 db "Do you want to overwrite file ",0
   355 000118C5 6E7420746F206F7665- <1>
   355 000118CE 727772697465206669- <1>
   355 000118D7 6C652000            <1>
   356                              <1>   
   357                              <1> Msg_DoYouWantCopyFile:
   358 000118DB 446F20796F75207761- <1>                 db "Do you want to copy file",0
   358 000118E4 6E7420746F20636F70- <1>
   358 000118ED 792066696C6500      <1>
   359                              <1> 
   360                              <1> Msg_read_file_error_before_EOF:
   361 000118F4 46696C652072656164- <1> 		db "File reading error! (before EOF)"
   361 000118FD 696E67206572726F72- <1>
   361 00011906 2120286265666F7265- <1>
   361 0001190F 20454F4629          <1>
   362 00011914 0A0A00              <1> 		db 0Ah, 0Ah, 0
   363                              <1> 
   364                              <1> ; 18/03/2016
   365                              <1> ; TRDOS 386 (v2.0) mainprog copy procedure
   366                              <1> msg_reading:
   367 00011917 52656164696E672E2E- <1> 		db "Reading... ", 0
   367 00011920 2E2000              <1>
   368                              <1> msg_writing:
   369 00011923 57726974696E672E2E- <1> 		db "Writing... ", 0
   369 0001192C 2E2000              <1>
   370                              <1> percentagestr:
   371 0001192F 2020202500          <1> 		db "   %", 0  ; "  0%" .. "100%"
   372                              <1> ; 11/04/2016
   373                              <1> Msg_No_Set_Space:
   374 00011934 496E73756666696369- <1>                 db "Insufficient environment space!"
   374 0001193D 656E7420656E766972- <1>
   374 00011946 6F6E6D656E74207370- <1>
   374 0001194F 61636521            <1>
   375 00011953 0D0A00              <1>                 db 0Dh, 0Ah, 0
   376                              <1> ; 18/04/2016
   377                              <1> isc_msg:	
   378 00011956 0D0A                <1> 		db 0Dh, 0Ah
   379 00011958 494E56414C49442053- <1> 		db "INVALID SYSTEM CALL", 0
   379 00011961 595354454D2043414C- <1>
   379 0001196A 4C00                <1>
   380                              <1> usi_msg:
   381 0001196C 0D0A                <1> 		db 0Dh, 0Ah
   382 0001196E 554E444546494E4544- <1> 		db "UNDEFINED SOFTWARE INTERRUPT", 0
   382 00011977 20534F465457415245- <1>
   382 00011980 20494E544552525550- <1>
   382 00011989 5400                <1>
   383                              <1> ifc_msg:
   384 0001198B 0D0A                <1> 		db 0Dh, 0Ah
   385 0001198D 494E56414C49442046- <1> 		db "INVALID FUNCTION CALL"
   385 00011996 554E4354494F4E2043- <1>
   385 0001199F 414C4C              <1>
   386                              <1> inv_msg_for_trdos_v2:
   387 000119A2 20                  <1> 		db 20h
   388 000119A3 666F72205452444F53- <1> 		db "for TRDOS v2!"
   388 000119AC 20763221            <1>
   389 000119B0 07                  <1> 		db 07h
   390 000119B1 0D0A                <1> 		db 0Dh, 0Ah
   391 000119B3 0D0A                <1> 		db 0Dh, 0Ah
   392 000119B5 494E5420            <1> 		db "INT "
   393 000119B9 303068              <1> int_num_str:	db "00h"
   394 000119BC 0D0A                <1> 		db 0Dh, 0Ah
   395 000119BE 454158203A20        <1> 		db "EAX : "
   396 000119C4 303030303030303068- <1> eax_str:	db "00000000h", 0Dh, 0Ah
   396 000119CD 0D0A                <1>
   397 000119CF 454950203A20        <1> 		db "EIP : "
   398 000119D5 303030303030303068- <1> eip_str:	db "00000000h", 0Dh, 0Ah, 0
   398 000119DE 0D0A00              <1>
   399                              <1> 
   400                              <1> ; 07/10/2016
   401                              <1> ; Device names & parameters (for kernel devices)
   402                              <1> 
   403 000119E1 90                  <1> align 2
   404                              <1> KDEV_NAME:
   405 000119E2 5454590000000000    <1> 		db 'TTY',0,0,0,0,0 ; 1
   406 000119EA 4D454D0000000000    <1> 		db 'MEM',0,0,0,0,0 ; 2
   407 000119F2 4644300000000000    <1> 		db 'FD0',0,0,0,0,0 ; 3
   408 000119FA 4644310000000000    <1> 		db 'FD1',0,0,0,0,0 ; 4
   409 00011A02 4844300000000000    <1> 		db 'HD0',0,0,0,0,0 ; 5
   410 00011A0A 4844310000000000    <1> 		db 'HD1',0,0,0,0,0 ; 6
   411 00011A12 4844320000000000    <1> 		db 'HD2',0,0,0,0,0 ; 7
   412 00011A1A 4844330000000000    <1> 		db 'HD3',0,0,0,0,0 ; 8
   413 00011A22 4C50540000000000    <1> 		db 'LPT',0,0,0,0,0 ; 9
   414 00011A2A 5454593000000000    <1> 		db 'TTY0',0,0,0,0 ; 10
   415 00011A32 5454593100000000    <1> 		db 'TTY1',0,0,0,0 ; 11
   416 00011A3A 5454593200000000    <1> 		db 'TTY2',0,0,0,0 ; 12
   417 00011A42 5454593300000000    <1> 		db 'TTY3',0,0,0,0 ; 13
   418 00011A4A 5454593400000000    <1> 		db 'TTY4',0,0,0,0 ; 14
   419 00011A52 5454593500000000    <1> 		db 'TTY5',0,0,0,0 ; 15
   420 00011A5A 5454593600000000    <1> 		db 'TTY6',0,0,0,0 ; 16
   421 00011A62 5454593700000000    <1> 		db 'TTY7',0,0,0,0 ; 17
   422 00011A6A 5454593800000000    <1> 		db 'TTY8',0,0,0,0 ; 18
   423 00011A72 5454593900000000    <1> 		db 'TTY9',0,0,0,0 ; 19
   424 00011A7A 434F4D3100000000    <1> 		db 'COM1',0,0,0,0 ; 18
   425 00011A82 434F4D3200000000    <1> 		db 'COM2',0,0,0,0 ; 19
   426                              <1> 		;db 'CONSOLE',0	  ; 1
   427                              <1> 		;db 'PRINTER',0   ; 9
   428                              <1> 		;db 'CDROM'	  ; 20
   429                              <1> 		;db 'CDROM0'	  ; 20
   430                              <1> 		;db 'CDROM1'	  ; 21		
   431                              <1> 		;db 'DVD'	  ; 22
   432                              <1> 		;db 'DVD0'	  ; 22
   433                              <1> 		;db 'DVD1'	  ; 23		
   434                              <1> 		;db 'USB'	  ; 24
   435                              <1> 		;db 'USB0'	  ; 24
   436                              <1> 		;db 'USB1'	  ; 25
   437                              <1> 		;db 'USB2'	  ; 26
   438                              <1> 		;db 'USB3'        ; 27
   439                              <1> 		;db 'KEYBOARD'	  ; 1	
   440                              <1> 		;db 'MOUSE'	  ; 28
   441                              <1> 		;db 'SOUND'	  ; 29
   442                              <1> 		;db 'VGA',0,0,0,0 ; 30
   443                              <1> 		;db 'CGA',0,0,0,0 ; 31
   444                              <1> 		;db 'AUDIO',0,0,0 ; 29
   445                              <1> 		;db 'VIDEO',0,0,0 ; 32
   446                              <1> 		;db 'MUSIC',0,0,0 ; 33
   447                              <1> 		;db 'ETHERNET'	  ; 34 		
   448                              <1> 		;db 'SD0',0,0,0,0,0 ; 35
   449                              <1> 		;db 'SD1',0,0,0,0,0 ; 36
   450                              <1> 		;db 'SD2',0,0,0,0,0 ; 37
   451                              <1> 		;db 'SD3',0,0,0,0,0 ; 38
   452                              <1> 		;db 'SATA0'	  ; 35
   453                              <1> 		;db 'SATA1'	  ; 36
   454                              <1> 		;db 'SATA2'        ; 37
   455                              <1> 		;db 'SATA3'        ; 38
   456                              <1> 		;db 'PATA0',0,0,0  ; 5
   457                              <1> 		;db 'PATA1',0,0,0  ; 6
   458                              <1> 		;db 'PATA2',0,0,0  ; 7
   459                              <1> 		;db 'PATA3',0,0,0  ; 8
   460                              <1> 		;db 'WIRELESS'	  ; 39
   461                              <1> 		;db 'HDMI',0,0,0,0 ; 40
   462 00011A8A 4E554C4C00000000    <1> 		db 'NULL',0,0,0,0 ; 0
   463                              <1> 
   464                              <1> NumOfKernelDevNames equ ($-KDEV_NAME) / 8 ; 20 (07/10/2016)
   465                              <1> 
   466                              <1> KDEV_NUMBER:
   467 00011A92 010203040506070809  <1> 		db 1,2,3,4,5,6,7,8,9
   468 00011A9B 0A0B0C0D0E0F101112- <1> 		db 10,11,12,13,14,15,16,17,18,19
   468 00011AA4 13                  <1>
   469 00011AA5 121300              <1> 		db 18,19,0
   470                              <1> 
   471                              <1> NumOfKernelDevices equ $ - KDEV_NUMBER
   472                              <1> 
   473                              <1> KDEV_OADDR:
   474 00011AA8 [C5120100]          <1> 		dd otty ;tty  ; 1
   475 00011AAC [C5120100]          <1> 		dd sret ;mem  ; 2
   476 00011AB0 [C5120100]          <1>  		dd sret ;fd0  ; 3
   477 00011AB4 [C5120100]          <1>  		dd sret ;fd1  ; 4
   478 00011AB8 [C5120100]          <1>  		dd sret ;hd0  ; 5
   479 00011ABC [C5120100]          <1>  		dd sret ;hd1  ; 6
   480 00011AC0 [C5120100]          <1>  		dd sret ;hd2  ; 7
   481 00011AC4 [C5120100]          <1>  		dd sret ;hd3  ; 8
   482 00011AC8 [C5120100]          <1>  		dd sret ;lpt  ; 9
   483 00011ACC [C5120100]          <1>  		dd ocvt ;tty0 ; 10
   484 00011AD0 [C5120100]          <1> 		dd ocvt ;tty1 ; 11
   485 00011AD4 [C5120100]          <1>  		dd ocvt ;tty2 ; 12
   486 00011AD8 [C5120100]          <1>  		dd ocvt ;tty3 ; 13
   487 00011ADC [C5120100]          <1>  		dd ocvt ;tty4 ; 14
   488 00011AE0 [C5120100]          <1>  		dd ocvt ;tty5 ; 15
   489 00011AE4 [C5120100]          <1>  		dd ocvt ;tty6 ; 16
   490 00011AE8 [C5120100]          <1>  		dd ocvt ;tty7 ; 17
   491 00011AEC [C5120100]          <1>  		dd ocvt ;tty8 ; 18
   492 00011AF0 [C5120100]          <1>  		dd ocvt ;tty9 ; 19
   493                              <1>  		;dd ocvt ;com1 ; 18
   494                              <1>  		;dd ocvt ;com2 ; 19
   495 00011AF4 [C5120100]          <1> 		dd sret ;null ; 20  
   496                              <1> KDEV_CADDR:
   497 00011AF8 [C5120100]          <1> 		dd ctty ;tty  ; 1
   498 00011AFC [C5120100]          <1> 		dd cret ;mem  ; 2
   499 00011B00 [C5120100]          <1>  		dd cret ;fd0  ; 3
   500 00011B04 [C5120100]          <1>  		dd cret ;fd1  ; 4
   501 00011B08 [C5120100]          <1>  		dd cret ;hd0  ; 5
   502 00011B0C [C5120100]          <1>  		dd cret ;hd1  ; 6
   503 00011B10 [C5120100]          <1>  		dd cret ;hd2  ; 7
   504 00011B14 [C5120100]          <1>  		dd cret ;hd3  ; 8
   505 00011B18 [C5120100]          <1>  		dd cret ;lpt  ; 9
   506 00011B1C [C5120100]          <1>  		dd ocvt ;tty0 ; 10
   507 00011B20 [C5120100]          <1> 		dd ccvt ;tty1 ; 11
   508 00011B24 [C5120100]          <1>  		dd ccvt ;tty2 ; 12
   509 00011B28 [C5120100]          <1>  		dd ccvt ;tty3 ; 13
   510 00011B2C [C5120100]          <1>  		dd ccvt ;tty4 ; 14
   511 00011B30 [C5120100]          <1>  		dd ccvt ;tty5 ; 15
   512 00011B34 [C5120100]          <1>  		dd ccvt ;tty6 ; 16
   513 00011B38 [C5120100]          <1>  		dd ccvt ;tty7 ; 17
   514 00011B3C [C5120100]          <1>  		dd ccvt ;tty8 ; 18
   515 00011B40 [C5120100]          <1>  		dd ccvt ;tty9 ; 19
   516                              <1>  		;dd ccvt ;com1 ; 18
   517                              <1>  		;dd ccvt ;com2 ; 19
   518 00011B44 [C5120100]          <1> 		dd cret ;null ; 20
   519                              <1> 
   520                              <1> KDEV_RADDR:
   521 00011B48 [C5120100]          <1> 		dd rtty ;tty  ; 1
   522 00011B4C [C5120100]          <1> 		dd rmem ;mem  ; 2
   523 00011B50 [C5120100]          <1>  		dd rfd  ;fd0  ; 3
   524 00011B54 [C5120100]          <1>  		dd rfd  ;fd1  ; 4
   525 00011B58 [C5120100]          <1>  		dd rhd  ;hd0  ; 5
   526 00011B5C [C5120100]          <1>  		dd rhd  ;hd1  ; 6
   527 00011B60 [C5120100]          <1>  		dd rhd  ;hd2  ; 7
   528 00011B64 [C5120100]          <1>  		dd rhd  ;hd3  ; 8
   529 00011B68 [C5120100]          <1>  		dd rlpt ;lpt  ; 9
   530 00011B6C [C5120100]          <1>  		dd rcvt ;tty0 ; 10
   531 00011B70 [C5120100]          <1> 		dd rcvt ;tty1 ; 11
   532 00011B74 [C5120100]          <1>  		dd rcvt ;tty2 ; 12
   533 00011B78 [C5120100]          <1>  		dd rcvt ;tty3 ; 13
   534 00011B7C [C5120100]          <1>  		dd rcvt ;tty4 ; 14
   535 00011B80 [C5120100]          <1>  		dd rcvt ;tty5 ; 15
   536 00011B84 [C5120100]          <1>  		dd rcvt ;tty6 ; 16
   537 00011B88 [C5120100]          <1>  		dd rcvt ;tty7 ; 17
   538 00011B8C [C5120100]          <1>  		dd rcvt ;tty8 ; 18
   539 00011B90 [C5120100]          <1>  		dd rcvt ;tty9 ; 19
   540                              <1>  		;dd rcvt ;com1 ; 18
   541                              <1>  		;dd rcvt ;com2 ; 19
   542 00011B94 [A9060100]          <1> 		dd rnull ;null ; 20  
   543                              <1> KDEV_WADDR:
   544 00011B98 [C5120100]          <1> 		dd wtty ;tty  ; 1
   545 00011B9C [C5120100]          <1> 		dd wmem ;mem  ; 2
   546 00011BA0 [C5120100]          <1>  		dd wfd  ;fd0  ; 3
   547 00011BA4 [C5120100]          <1>  		dd wfd  ;fd1  ; 4
   548 00011BA8 [C5120100]          <1>  		dd whd  ;hd0  ; 5
   549 00011BAC [C5120100]          <1>  		dd whd  ;hd1  ; 6
   550 00011BB0 [C5120100]          <1>  		dd whd  ;hd2  ; 7
   551 00011BB4 [C5120100]          <1>  		dd whd  ;hd3  ; 8
   552 00011BB8 [C5120100]          <1>  		dd wlpt ;lpt  ; 9
   553 00011BBC [C5120100]          <1>  		dd xmtt ;tty0 ; 10
   554 00011BC0 [C5120100]          <1> 		dd xmtt ;tty1 ; 11
   555 00011BC4 [C5120100]          <1>  		dd xmtt ;tty2 ; 12
   556 00011BC8 [C5120100]          <1>  		dd xmtt ;tty3 ; 13
   557 00011BCC [C5120100]          <1>  		dd xmtt ;tty4 ; 14
   558 00011BD0 [C5120100]          <1>  		dd xmtt ;tty5 ; 15
   559 00011BD4 [C5120100]          <1>  		dd xmtt ;tty6 ; 16
   560 00011BD8 [C5120100]          <1>  		dd xmtt ;tty7 ; 17
   561 00011BDC [C5120100]          <1>  		dd xmtt ;tty8 ; 18
   562 00011BE0 [C5120100]          <1>  		dd xmtt ;tty9 ; 19
   563                              <1>  		;dd xmtt ;com1 ; 18
   564                              <1>  		;dd xmtt ;com2 ; 19
   565 00011BE4 [AA060100]          <1> 		dd wnull ;null ; 20  
   566                              <1> 
   567                              <1> ; DEV_ACCESS bits:
   568                              <1> 	; bit 0 = accessable by normal users
   569                              <1> 	; bit 1 = read access permission
   570                              <1> 	; bit 2 = write access permission
   571                              <1> 	; bit 3 = IOCTL permission to users
   572                              <1> 	; bit 4 = block device if it is set
   573                              <1> 	; bit 5 = 16 bit or 1024 byte data
   574                              <1> 	; bit 6 = 32 bit or 2048 byte data
   575                              <1> 	; bit 7 = installable device driver	
   576                              <1> 
   577                              <1> KDEV_ACCESS: ; 08/10/2016
   578 00011BE8 07                  <1> 		db  00000111b	; tty, 1
   579 00011BE9 07                  <1> 		db  00000111b	; mem, 2	
   580 00011BEA 8F                  <1> 		db  10001111b	; fd0, 3	
   581 00011BEB 8F                  <1> 		db  10001111b	; fd1, 4
   582 00011BEC 8F                  <1> 		db  10001111b	; hd0, 5
   583 00011BED 8F                  <1> 		db  10001111b	; hd1, 6
   584 00011BEE 8F                  <1> 		db  10001111b	; hd2, 7
   585 00011BEF 8F                  <1> 		db  10001111b	; hd3, 8
   586 00011BF0 07                  <1> 		db  00000111b   ; lpt, 9
   587 00011BF1 07                  <1> 		db  00000111b	; tty0, 10
   588 00011BF2 07                  <1> 		db  00000111b	; tty1, 11
   589 00011BF3 07                  <1> 		db  00000111b	; tty2, 12
   590 00011BF4 07                  <1> 		db  00000111b	; tty3, 13
   591 00011BF5 07                  <1> 		db  00000111b	; tty4, 14
   592 00011BF6 07                  <1> 		db  00000111b	; tty5, 15
   593 00011BF7 07                  <1> 		db  00000111b	; tty6, 16
   594 00011BF8 07                  <1> 		db  00000111b	; tty7, 17
   595 00011BF9 07                  <1> 		db  00000111b	; tty8, 18
   596 00011BFA 07                  <1> 		db  00000111b	; tty9, 19
   597                              <1> 		;db 00000111b	; com1, 18
   598                              <1> 		;db 00000111b	; com2, 19
   599 00011BFB 00                  <1> 		db  00000000b   ; null, 0
   600                              <1> 
   601                              <1> ; 07/10/2016
   602                              <1> NumOfInstallableDevices equ 8
   603                              <1> NUMIDEV		equ NumOfInstallableDevices ; 8
   604                              <1> NUMOFDEVICES	equ NumOfKernelDevices + NumOfInstallableDevices
   605                              <1> 
   606                              <1> ; 26/02/2017
   607                              <1> ; IRQ Callback (& Signal Response Byte) service availibity
   608                              <1> ; 'syscalbac'
   609                              <1> ; ***************************************************
   610                              <1> ; IRQ 00 01 02 03 04 05 06 07 08 09 10 11 12 13 14 15
   611                              <1> ; --- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- --
   612                              <1> ; --- 00 00 00 01 02 03 00 04 00 05 06 07 08 09 00 00
   613                              <1> ; ***************************************************
   614                              <1> IRQenum:
   615 00011BFC 000000010203000400- <1> 	db  0,0,0,1,2,3,0,4,0,5,6,7,8,9,0,0
   615 00011C05 05060708090000      <1>
   616                              <1> 
   617                              <1> ; 28/08/2017
   618                              <1> ; 20/08/2017
   619                              <1> ; DMA Registers (for 'sysdma')
   620                              <1> ; 02/07/2017 (sb16mod.s)
   621 00011C0C 00020406C0C4C8CC    <1> dma_adr:	db 0,2,4,6,0C0h,0C4h,0C8h,0CCh
   622 00011C14 01030507C2C6CACE    <1> dma_cnt:	db 1,3,5,7,0C2h,0C6h,0CAh,0CEh
   623 00011C1C 878381828F8B898A    <1> dma_page:	db 87h,83h,81h,82h,8Fh,8Bh,89h,8Ah ; 03/08/2017
   624 00011C24 0A0A0A0AD4D4D4D4    <1> dma_mask:	db 0Ah,0Ah,0Ah,0Ah,0D4h,0D4h,0D4h,0D4h
   625 00011C2C 0B0B0B0BD6D6D6D6    <1> dma_mod:	db 0Bh,0Bh,0Bh,0Bh,0D6h,0D6h,0D6h,0D6h
   626 00011C34 0C0C0C0CD8D8D8D8    <1> dma_flip:	db 0Ch,0Ch,0Ch,0Ch,0D8h,0D8h,0D8h,0D8h	
  2870                                  
  2871                                  ; 27/08/2014
  2872                                  scr_row:
  2873 00011C3C E0810B00                	dd 0B8000h + 0A0h + 0A0h + 0A0h ; Row 3
  2874                                  scr_col:
  2875 00011C40 00000000                	dd 0
  2876                                  
  2877                                  Align 4
  2878                                  	; 15/04/2016
  2879                                  	; TRDOS 386 (TRDOS v2.0)
  2880                                  
  2881                                  	; 21/08/2014
  2882                                  ilist:
  2883                                  	;times 	32 dd cpu_except ; INT 0 to INT 1Fh
  2884                                  	;
  2885                                  	; Exception list
  2886                                  	; 25/08/2014	
  2887 00011C44 [5B0B0000]              	dd	exc0	; 0h,  Divide-by-zero Error
  2888 00011C48 [620B0000]              	dd	exc1	
  2889 00011C4C [690B0000]              	dd 	exc2	
  2890 00011C50 [700B0000]              	dd	exc3	
  2891 00011C54 [740B0000]              	dd	exc4	
  2892 00011C58 [780B0000]              	dd	exc5	
  2893 00011C5C [7C0B0000]              	dd 	exc6	; 06h,  Invalid Opcode
  2894 00011C60 [800B0000]              	dd	exc7	
  2895 00011C64 [840B0000]              	dd	exc8	
  2896 00011C68 [880B0000]              	dd	exc9	
  2897 00011C6C [8C0B0000]              	dd 	exc10	
  2898 00011C70 [900B0000]              	dd	exc11
  2899 00011C74 [940B0000]              	dd	exc12
  2900 00011C78 [980B0000]              	dd	exc13	; 0Dh, General Protection Fault
  2901 00011C7C [9C0B0000]              	dd 	exc14	; 0Eh, Page Fault
  2902 00011C80 [A00B0000]              	dd	exc15
  2903 00011C84 [A40B0000]              	dd	exc16
  2904 00011C88 [A80B0000]              	dd	exc17
  2905 00011C8C [AC0B0000]              	dd 	exc18
  2906 00011C90 [B00B0000]              	dd	exc19
  2907 00011C94 [B40B0000]              	dd 	exc20
  2908 00011C98 [B80B0000]              	dd	exc21
  2909 00011C9C [BC0B0000]              	dd	exc22
  2910 00011CA0 [C00B0000]              	dd	exc23
  2911 00011CA4 [C40B0000]              	dd 	exc24
  2912 00011CA8 [C80B0000]              	dd	exc25
  2913 00011CAC [CC0B0000]              	dd	exc26
  2914 00011CB0 [D00B0000]              	dd	exc27
  2915 00011CB4 [D40B0000]              	dd 	exc28
  2916 00011CB8 [D80B0000]              	dd	exc29
  2917 00011CBC [DC0B0000]              	dd 	exc30
  2918 00011CC0 [E00B0000]              	dd	exc31
  2919                                  IRQ_list: ; 28/02/2017 ('syscalbac')
  2920                                  	; Interrupt list
  2921 00011CC4 [CF080000]              	dd	timer_int	; INT 20h
  2922                                  		;dd	irq0	
  2923 00011CC8 [43100000]              	dd	kb_int		; 24/01/2016
  2924                                  		;dd	irq1
  2925 00011CCC [B10A0000]              	dd	irq2
  2926                                  		; COM2 int
  2927 00011CD0 [B50A0000]              	dd	irq3
  2928                                  		; COM1 int
  2929 00011CD4 [C00A0000]              	dd	irq4
  2930 00011CD8 [CB0A0000]              	dd	irq5
  2931                                  ;DISKETTE_INT: ;06/02/2015
  2932 00011CDC [E5480000]              	dd	fdc_int		; 16/02/2015, IRQ 6 handler	
  2933                                  		;dd	irq6
  2934                                  ; Default IRQ 7 handler against spurious IRQs (from master PIC)
  2935                                  ; 25/02/2015 (source: http://wiki.osdev.org/8259_PIC)
  2936 00011CE0 [3A0E0000]              	dd	default_irq7	; 25/02/2015
  2937                                  		;dd	irq7
  2938                                  ; Real Time Clock Interrupt
  2939 00011CE4 [3A0A0000]              	dd	rtc_int		; 23/02/2015, IRQ 8 handler
  2940                                  		;dd	irq8	; INT 28h
  2941 00011CE8 [DB0A0000]              	dd	irq9
  2942 00011CEC [DF0A0000]              	dd	irq10
  2943 00011CF0 [E30A0000]              	dd	irq11
  2944 00011CF4 [E70A0000]              	dd	irq12
  2945 00011CF8 [EB0A0000]              	dd	irq13
  2946                                  ;HDISK_INT1:  ;06/02/2015 	
  2947 00011CFC [98520000]              	dd	hdc1_int 	; 21/02/2015, IRQ 14 handler		
  2948                                  		;dd	irq14
  2949                                  ;HDISK_INT2:  ;06/02/2015
  2950 00011D00 [BF520000]              	dd	hdc2_int 	; 21/02/2015, IRQ 15 handler		
  2951                                  		;dd	irq15	; INT 2Fh
  2952                                  		; 14/08/2015
  2953                                  	;dd	sysent		; INT 30h (system calls)
  2954                                  
  2955                                  	; 15/04/2016
  2956                                  	; TRDOS 386(TRDOS v2.0) Software Interrupts
  2957                                  
  2958 00011D04 [611D0100]              	dd	int30h		; Reserved for
  2959                                  				; !!! Retro UNIX (RUNIX) !!!
  2960                                  				; !!! SINGLIX !!! System Calls
  2961 00011D08 [36170000]              	dd	int31h		; Video BIOS (IBM PC/AT, Int 10h)
  2962 00011D0C [620E0000]              	dd	int32h		; Keyboard Functions (IBM PC/AT, Int 16h)
  2963 00011D10 [9C490000]              	dd	int33h		; DISK I/O (IBM PC/AT, Int 13h)
  2964 00011D14 [5CFF0000]              	dd	int34h		; #IOCTL# (I/O port access support for ring 3)
  2965 00011D18 [ED600000]              	dd	int35h		; Time/Date Functions (IBM PC/AT, Int 1Ah)
  2966 00011D1C [EE0C0000]              	dd	ignore_int	; INT 36h : Timer Functions	
  2967 00011D20 [EE0C0000]              	dd	ignore_int	; INT 37h	
  2968 00011D24 [EE0C0000]              	dd	ignore_int	; INT 38h
  2969 00011D28 [EE0C0000]              	dd	ignore_int	; INT 39h
  2970 00011D2C [EE0C0000]              	dd	ignore_int	; INT 3Ah	
  2971 00011D30 [EE0C0000]              	dd	ignore_int	; INT 3Bh
  2972 00011D34 [EE0C0000]              	dd	ignore_int	; INT 3Ch
  2973 00011D38 [EE0C0000]              	dd	ignore_int	; INT 3Dh	
  2974 00011D3C [EE0C0000]              	dd	ignore_int	; INT 3Eh
  2975 00011D40 [EE0C0000]              	dd	ignore_int	; INT 3Fh
  2976 00011D44 [48CE0000]              	dd	sysent		; INT 40h : !!! TRDOS 386 System Calls !!!
  2977                                  	;dd	ignore_int
  2978 00011D48 00000000                	dd	0
  2979                                  
  2980                                  ; 20/08/2014
  2981                                    ; /* This is the default interrupt "handler" :-) */ 
  2982                                    ; Linux v0.12 (head.s)
  2983                                  int_msg:
  2984 00011D4C 556E6B6E6F776E2069-     	db "Unknown interrupt ! ", 0
  2984 00011D55 6E7465727275707420-
  2984 00011D5E 212000             
  2985                                  
  2986                                  ; 15/04/2016
  2987                                  ; TRDOS 386 (TRDOS v2.0)
  2988                                  
  2989                                  ; 29/04/2016
  2990                                  int30h:
  2991                                  trdos_isc_routine:
  2992                                  	; 02/05/2016
  2993                                  	; 01/05/2016
  2994                                  	; 29/04/2016
  2995                                  	; 18/04/2016
  2996                                  	; 15/04/2016 (TRDOS 386 = TRDOS v2.0)
  2997                                  	; 17/04/2011 (TRDOS v1.0, 'IFC.ASM')
  2998                                  	; 03/02/2011 ('trdos_ifc_routine')
  2999                                  	;
  3000 00011D61 8B1C24                  	mov	ebx, [esp] ; EIP (next)
  3001 00011D64 83EB02                  	sub	ebx, 2 ; EIP (CD ##h)
  3002                                  
  3003 00011D67 89C1                    	mov	ecx, eax
  3004 00011D69 8A4301                  	mov	al, [ebx+1] ; CDh ##h
  3005                                  
  3006 00011D6C 66BA1000                	mov	dx, KDATA
  3007 00011D70 8EDA                    	mov	ds, dx
  3008 00011D72 8EC2                    	mov	es, dx
  3009                                  
  3010 00011D74 FC                      	cld
  3011 00011D75 8B15[805E0100]          	mov	edx, [k_page_dir]
  3012 00011D7B 0F22DA                  	mov	cr3, edx
  3013                                  
  3014 00011D7E E85D1CFFFF              	call	bytetohex
  3015 00011D83 66A3[B9190100]          	mov	[int_num_str], ax
  3016                                  
  3017 00011D89 89D8                    	mov	eax, ebx ; EIP
  3018 00011D8B E8901CFFFF              	call	dwordtohex
  3019 00011D90 8915[D5190100]          	mov	[eip_str], edx
  3020 00011D96 A3[D9190100]            	mov	[eip_str+4], eax
  3021                                  
  3022 00011D9B 89C8                    	mov	eax, ecx
  3023 00011D9D E87E1CFFFF              	call	dwordtohex
  3024 00011DA2 8915[C4190100]          	mov	[eax_str], edx
  3025 00011DA8 A3[C8190100]            	mov	[eax_str+4], eax 	
  3026                                  
  3027 00011DAD 43                      	inc	ebx
  3028 00011DAE 8A03                    	mov	al, [ebx] ; Interrupt number
  3029                                  
  3030                                  trdos_isc_handler:
  3031 00011DB0 80FE30                  	cmp	dh, 30h ; Retro UNIX, SINGLIX System calls
  3032 00011DB3 7507                    	jne	short trdos_usi_handler
  3033 00011DB5 BE[56190100]            	mov	esi, isc_msg
  3034 00011DBA EB05                    	jmp	short loc_write_inv_system_call_msg
  3035                                  
  3036                                  trdos_usi_handler:
  3037 00011DBC BE[6C190100]            	mov	esi, usi_msg
  3038                                  
  3039                                  loc_write_inv_system_call_msg:
  3040 00011DC1 E83F4EFFFF              	call	print_msg
  3041                                  	; 29/04/2016
  3042 00011DC6 BE[A2190100]            	mov	esi, inv_msg_for_trdos_v2
  3043 00011DCB E8354EFFFF              	call	print_msg
  3044                                  
  3045                                  loc_ifc_terminate_process:
  3046                                  	; u.uno = process number
  3047                                  	; 29/04/2016
  3048                                  
  3049                                  	; 02/05/2016
  3050 00011DD0 FE05[5B030300]          	inc	byte [sysflg] ; 0FFh -> 0
  3051                                  
  3052 00011DD6 B801000000              	mov	eax, 1
  3053 00011DDB E941B3FFFF              	jmp	sysexit
  3054                                  
  3055                                  ; 07/03/2015
  3056                                  ; Temporary Code
  3057                                  display_disks:
  3058 00011DE0 803D[AE640000]00        	cmp 	byte [fd0_type], 0
  3059 00011DE7 7605                    	jna 	short ddsks1
  3060 00011DE9 E87D000000              	call	pdskm
  3061                                  ddsks1:
  3062 00011DEE 803D[AF640000]00        	cmp	byte [fd1_type], 0
  3063 00011DF5 760C                    	jna	short ddsks2
  3064 00011DF7 C605[3B1F0100]31        	mov	byte [dskx], '1'
  3065 00011DFE E868000000              	call	pdskm
  3066                                  ddsks2:
  3067 00011E03 803D[B0640000]00        	cmp	byte [hd0_type], 0
  3068 00011E0A 7654                    	jna	short ddsk6
  3069 00011E0C 66C705[391F0100]68-     	mov	word [dsktype], 'hd'
  3069 00011E14 64                 
  3070 00011E15 C605[3B1F0100]30        	mov	byte [dskx], '0'
  3071 00011E1C E84A000000              	call	pdskm
  3072                                  ddsks3:
  3073 00011E21 803D[B1640000]00        	cmp	byte [hd1_type], 0
  3074 00011E28 7636                    	jna	short ddsk6
  3075 00011E2A C605[3B1F0100]31        	mov	byte [dskx], '1'
  3076 00011E31 E835000000              	call	pdskm
  3077                                  ddsks4:
  3078 00011E36 803D[B2640000]00        	cmp	byte [hd2_type], 0
  3079 00011E3D 7621                    	jna	short ddsk6
  3080 00011E3F C605[3B1F0100]32        	mov	byte [dskx], '2'
  3081 00011E46 E820000000              	call	pdskm
  3082                                  ddsks5:
  3083 00011E4B 803D[B3640000]00        	cmp	byte [hd3_type], 0
  3084 00011E52 760C                    	jna	short ddsk6
  3085 00011E54 C605[3B1F0100]33        	mov	byte [dskx], '3'
  3086 00011E5B E80B000000              	call	pdskm
  3087                                  ddsk6:
  3088 00011E60 BE[631F0100]            	mov	esi, nextline
  3089 00011E65 E806000000              	call	pdskml
  3090                                  pdskm_ok:
  3091 00011E6A C3                      	retn
  3092                                  pdskm:
  3093 00011E6B BE[371F0100]            	mov	esi, dsk_ready_msg
  3094                                  pdskml:	
  3095 00011E70 AC                      	lodsb
  3096 00011E71 08C0                    	or	al, al
  3097 00011E73 74F5                    	jz	short pdskm_ok
  3098 00011E75 56                      	push	esi
  3099                                  	; 13/05/2016
  3100 00011E76 BB07000000                      mov     ebx, 7  ; Black background, 
  3101                                  			; light gray forecolor
  3102                                  			; Video page 0 (bh=0)
  3103 00011E7B E85502FFFF              	call	_write_tty
  3104 00011E80 5E                      	pop	esi
  3105 00011E81 EBED                    	jmp	short pdskml
  3106                                  
  3107 00011E83 90                      Align 2
  3108                                  	; 21/08/2014
  3109                                  exc_msg:
  3110 00011E84 435055206578636570-     	db "CPU exception ! "
  3110 00011E8D 74696F6E202120     
  3111                                  excnstr: 		; 25/08/2014
  3112 00011E94 3F3F68202045495020-     	db "??h", "  EIP : "
  3112 00011E9D 3A20               
  3113                                  EIPstr: ; 29/08/2014
  3114 00011E9F 00<rept>                	times 12 db 0
  3115                                  
  3116                                  	; 23/02/2015
  3117                                  	; 25/08/2014
  3118                                  ;scounter:
  3119                                  ;	db 5
  3120                                  ;	db 19
  3121                                  
  3122                                  ; 06/11/2014
  3123                                  ; Memory Information message
  3124                                  ; 14/08/2015
  3125                                  msg_memory_info:
  3126 00011EAB 07                      	db	07h
  3127 00011EAC 0D0A                    	db	0Dh, 0Ah
  3128                                  	;db 	"MEMORY ALLOCATION INFO", 0Dh, 0Ah, 0Dh, 0Ah
  3129 00011EAE 546F74616C206D656D-     	db	"Total memory : "
  3129 00011EB7 6F7279203A20       
  3130                                  mem_total_b_str: ; 10 digits
  3131 00011EBD 303030303030303030-     	db	"0000000000 bytes", 0Dh, 0Ah
  3131 00011EC6 302062797465730D0A 
  3132 00011ECF 202020202020202020-     	db	"               ", 20h, 20h, 20h
  3132 00011ED8 202020202020202020 
  3133                                  mem_total_p_str: ; 7 digits
  3134 00011EE1 303030303030302070-     	db	"0000000 pages", 0Dh, 0Ah
  3134 00011EEA 616765730D0A       
  3135 00011EF0 0D0A                    	db 	0Dh, 0Ah
  3136 00011EF2 46726565206D656D6F-     	db	"Free memory  : "
  3136 00011EFB 727920203A20       
  3137                                  free_mem_b_str:  ; 10 digits
  3138 00011F01 3F3F3F3F3F3F3F3F3F-     	db	"?????????? bytes", 0Dh, 0Ah
  3138 00011F0A 3F2062797465730D0A 
  3139 00011F13 202020202020202020-     	db	"               ", 20h, 20h, 20h
  3139 00011F1C 202020202020202020 
  3140                                  free_mem_p_str:  ; 7 digits
  3141 00011F25 3F3F3F3F3F3F3F2070-     	db	"??????? pages", 0Dh, 0Ah
  3141 00011F2E 616765730D0A       
  3142 00011F34 0D0A00                  	db	0Dh, 0Ah, 0
  3143                                  
  3144                                  dsk_ready_msg:
  3145 00011F37 0D0A                    	db 	0Dh, 0Ah
  3146                                  dsktype:
  3147 00011F39 6664                    	db	'fd'
  3148                                  dskx:
  3149 00011F3B 30                      	db	'0'
  3150 00011F3C 20                      	db	20h
  3151 00011F3D 697320524541445920-     	db 	'is READY ...'
  3151 00011F46 2E2E2E             
  3152 00011F49 00                      	db 	0
  3153                                  
  3154                                  setup_error_msg:
  3155 00011F4A 0D0A                    	db 0Dh, 0Ah
  3156 00011F4C 4469736B2053657475-     	db 'Disk Setup Error !' 
  3156 00011F55 70204572726F722021 
  3157 00011F5E 0D0A00                  	db 0Dh, 0Ah,0
  3158                                  
  3159                                  next2line: ; 08/02/2016
  3160 00011F61 0D0A                    	db	0Dh, 0Ah
  3161                                  nextline:
  3162 00011F63 0D0A00                  	db 	0Dh, 0Ah, 0
  3163                                  
  3164                                  ; KERNEL - SYSINIT Messages
  3165                                  ; 24/08/2015
  3166                                  ; 13/04/2015 - (Retro UNIX 386 v1 Beginning)
  3167                                  ; 14/07/2013
  3168                                  ;kernel_init_err_msg:
  3169                                  ;	db 0Dh, 0Ah
  3170                                  ;	db 07h
  3171                                  ;	db 'Kernel initialization ERROR !'
  3172                                  ;	db 0Dh, 0Ah, 0 
  3173                                  
  3174                                  ;welcome_msg: 
  3175                                  ;	db 0Dh, 0Ah
  3176                                  ;	db 07h
  3177                                  ;	db 'Welcome to TRDOS 386 Operating System !'
  3178                                  ;	db 0Dh, 0Ah
  3179                                  ;	db 'by Erdogan Tan - 31/12/2017 (v2.0.0)'
  3180                                  ;	db 0Dh, 0Ah, 0
  3181                                  
  3182                                  panic_msg:
  3183 00011F66 0D0A07                  	db 0Dh, 0Ah, 07h
  3184 00011F69 4552524F523A204B65-     	db 'ERROR: Kernel Panic !'
  3184 00011F72 726E656C2050616E69-
  3184 00011F7B 632021             
  3185 00011F7E 0D0A00                  	db 0Dh, 0Ah, 0
  3186                                  
  3187                                  ;msgl_drv_not_ready: 
  3188                                  ;	db 07h, 0Dh, 0Ah
  3189                                  ;       db 'Drive not ready or read error !'
  3190                                  ;       db 0Dh, 0Ah, 0
  3191                                  
  3192                                  starting_msg:
  3193 00011F81 5475726B6973682052-     	db "Turkish Rational DOS v2.0 [30/11/2020] ...", 0
  3193 00011F8A 6174696F6E616C2044-
  3193 00011F93 4F532076322E30205B-
  3193 00011F9C 33302F31312F323032-
  3193 00011FA5 305D202E2E2E00     
  3194                                  NextLine:
  3195 00011FAC 0D0A00                  	db 0Dh, 0Ah, 0
  3196                                  
  3197                                  %include 'audio.s' ; 03/04/2017
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.2 - audio.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 01/09/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 03/04/2017
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ****************************************************************************
    10                              <1> 
    11                              <1> ; AUDIO CONTROLLER & CODEC DEFINITIONS & CODE FOR TRDOS 386
    12                              <1> 
    13                              <1> ;=============================================================================
    14                              <1> ;               EQUATES
    15                              <1> ;=============================================================================
    16                              <1> 
    17                              <1> ; PCI EQUATES
    18                              <1> 
    19                              <1> BIT0  EQU 1
    20                              <1> BIT1  EQU 2
    21                              <1> BIT2  EQU 4
    22                              <1> BIT3  EQU 8
    23                              <1> BIT4  EQU 10h
    24                              <1> BIT5  EQU 20h
    25                              <1> BIT6  EQU 40h
    26                              <1> BIT7  EQU 80h
    27                              <1> BIT8  EQU 100h
    28                              <1> BIT9  EQU 200h
    29                              <1> BIT10 EQU 400h
    30                              <1> BIT11 EQU 800h
    31                              <1> BIT12 EQU 1000h
    32                              <1> BIT13 EQU 2000h
    33                              <1> BIT14 EQU 4000h
    34                              <1> BIT15 EQU 8000h
    35                              <1> BIT16 EQU 10000h
    36                              <1> BIT17 EQU 20000h
    37                              <1> BIT18 EQU 40000h
    38                              <1> BIT19 EQU 80000h
    39                              <1> BIT20 EQU 100000h
    40                              <1> BIT21 EQU 200000h
    41                              <1> BIT22 EQU 400000h
    42                              <1> BIT23 EQU 800000h
    43                              <1> BIT24 EQU 1000000h
    44                              <1> BIT25 EQU 2000000h
    45                              <1> BIT26 EQU 4000000h
    46                              <1> BIT27 EQU 8000000h
    47                              <1> BIT28 EQU 10000000h
    48                              <1> BIT29 EQU 20000000h
    49                              <1> BIT30 EQU 40000000h
    50                              <1> BIT31 EQU 80000000h
    51                              <1> NOT_BIT31 EQU 7FFFFFFFh
    52                              <1> 
    53                              <1> ; PCI equates
    54                              <1> ; PCI function address (PFA)
    55                              <1> ; bit 31 = 1
    56                              <1> ; bit 23:16 = bus number     (0-255)
    57                              <1> ; bit 15:11 = device number  (0-31)
    58                              <1> ; bit 10:8 = function number (0-7)
    59                              <1> ; bit 7:0 = register number  (0-255)
    60                              <1> 
    61                              <1> IO_ADDR_MASK    EQU     0FFFEh	; mask off bit 0 for reading BARs
    62                              <1> PCI_INDEX_PORT  EQU     0CF8h
    63                              <1> PCI_DATA_PORT   EQU     0CFCh
    64                              <1> PCI32           EQU     BIT31	; bitflag to signal 32bit access
    65                              <1> PCI16           EQU     BIT30	; bitflag for 16bit access
    66                              <1> NOT_PCI32_PCI16	EQU	03FFFFFFFh ; NOT BIT31+BIT30 ; 19/03/2017
    67                              <1> 
    68                              <1> PCI_FN0         EQU     0 << 8
    69                              <1> PCI_FN1         EQU     1 << 8
    70                              <1> PCI_FN2         EQU     2 << 8
    71                              <1> PCI_FN3         EQU     3 << 8
    72                              <1> PCI_FN4         EQU     4 << 8
    73                              <1> PCI_FN5         EQU     5 << 8
    74                              <1> PCI_FN6         EQU     6 << 8
    75                              <1> PCI_FN7         EQU     7 << 8
    76                              <1> 
    77                              <1> PCI_CMD_REG	EQU	04h	; reg 04, command reg
    78                              <1> IO_ENA		EQU	BIT0	; i/o decode enable
    79                              <1> MEM_ENA		EQU	BIT1	; memory decode enable
    80                              <1> BM_ENA		EQU     BIT2	; bus master enable
    81                              <1> 
    82                              <1> ; VIA VT8233 EQUATES
    83                              <1> 
    84                              <1> VIA_VID		equ 1106h	; VIA's PCI vendor ID
    85                              <1> VT8233_DID      equ 3059h	; VT8233 (VT8235) device ID
    86                              <1> 		
    87                              <1> PCI_IO_BASE          equ 10h
    88                              <1> AC97_INT_LINE        equ 3Ch
    89                              <1> VIA_ACLINK_CTRL      equ 41h
    90                              <1> VIA_ACLINK_STAT      equ 40h
    91                              <1> VIA_ACLINK_C00_READY equ 01h ; primary codec ready
    92                              <1> 	
    93                              <1> VIA_REG_AC97	     equ 80h ; dword
    94                              <1> 
    95                              <1> VIA_ACLINK_CTRL_ENABLE	equ   80h ; 0: disable, 1: enable
    96                              <1> VIA_ACLINK_CTRL_RESET	equ   40h ; 0: assert, 1: de-assert
    97                              <1> VIA_ACLINK_CTRL_SYNC	equ   20h ; 0: release SYNC, 1: force SYNC hi
    98                              <1> VIA_ACLINK_CTRL_VRA	equ   08h ; 0: disable VRA, 1: enable VRA
    99                              <1> VIA_ACLINK_CTRL_PCM	equ   04h ; 0: disable PCM, 1: enable PCM
   100                              <1> 					; 3D Audio Channel slots 3/4
   104                              <1> VIA_ACLINK_CTRL_INIT	equ  (VIA_ACLINK_CTRL_ENABLE +                               VIA_ACLINK_CTRL_RESET +                               VIA_ACLINK_CTRL_PCM +                               VIA_ACLINK_CTRL_VRA)
   105                              <1> 
   106                              <1> CODEC_AUX_VOL		equ   04h
   107                              <1> VIA_REG_AC97_BUSY	equ   01000000h ;(1<<24) 
   108                              <1> VIA_REG_AC97_CMD_SHIFT	equ   10h ; 16
   109                              <1> VIA_REG_AC97_PRIMARY_VALID equ 02000000h ;(1<<25)
   110                              <1> VIA_REG_AC97_READ	equ   00800000h ;(1<<23)
   111                              <1> VIA_REG_AC97_CODEC_ID_SHIFT   equ  1Eh ; 30
   112                              <1> VIA_REG_AC97_CODEC_ID_PRIMARY equ  0
   113                              <1> VIA_REG_AC97_DATA_SHIFT equ   0
   114                              <1> VIADEV_PLAYBACK         equ   0
   115                              <1> VIA_REG_OFFSET_STATUS   equ   0    ;; byte - channel status
   116                              <1> VIA_REG_OFFSET_CONTROL  equ   01h  ;; byte - channel control
   117                              <1> VIA_REG_CTRL_START	equ   80h  ;; WO
   118                              <1> VIA_REG_CTRL_TERMINATE  equ   40h  ;; WO
   119                              <1> VIA_REG_CTRL_PAUSE      equ   08h  ;; RW
   120                              <1> VIA_REG_CTRL_RESET      equ   01h  ;; RW - probably reset? undocumented
   121                              <1> VIA_REG_OFFSET_STOP_IDX equ   08h  ;; dword - stop index, channel type, sample rate
   122                              <1> VIA8233_REG_TYPE_16BIT  equ   200000h ;; RW
   123                              <1> VIA8233_REG_TYPE_STEREO equ   100000h ;; RW
   124                              <1> VIA_REG_OFFSET_CURR_INDEX equ 0Fh ;; byte - channel current index (for via8233 only)
   125                              <1> VIA_REG_OFFSET_TABLE_PTR equ  04h  ;; dword - channel table pointer
   126                              <1> VIA_REG_OFFSET_CURR_PTR equ   04h  ;; dword - channel current pointer
   127                              <1> VIA_REG_OFS_PLAYBACK_VOLUME_L equ  02h ;; byte
   128                              <1> VIA_REG_OFS_PLAYBACK_VOLUME_R equ  03h ;; byte
   129                              <1> VIA_REG_CTRL_AUTOSTART	equ   20h
   130                              <1> VIA_REG_CTRL_INT_EOL	equ   02h
   131                              <1> VIA_REG_CTRL_INT_FLAG	equ   01h
   134                              <1> VIA_REG_CTRL_INT	equ  (VIA_REG_CTRL_INT_FLAG +                               VIA_REG_CTRL_INT_EOL +                               VIA_REG_CTRL_AUTOSTART)
   135                              <1> 
   136                              <1> VIA_REG_STAT_STOP_IDX	equ   10h    ;; RO ; 27/07/2020
   137                              <1> 				     ; current index = stop index
   138                              <1> VIA_REG_STAT_STOPPED	equ   04h    ;; RWC
   139                              <1> VIA_REG_STAT_EOL	equ   02h    ;; RWC
   140                              <1> VIA_REG_STAT_FLAG	equ   01h    ;; RWC
   141                              <1> VIA_REG_STAT_ACTIVE	equ   80h    ;; RO
   142                              <1> ; 28/11/2016
   143                              <1> VIA_REG_STAT_LAST	equ   40h    ;; RO
   144                              <1> VIA_REG_STAT_TRIGGER_QUEUED equ 08h  ;; RO
   145                              <1> VIA_REG_CTRL_INT_STOP	equ   04h  ; Interrupt on Current Index = Stop Index
   146                              <1> 		   		   ; and End of Block
   147                              <1> 
   148                              <1> VIA_REG_OFFSET_CURR_COUNT equ 0Ch ;; dword - channel current count, index
   149                              <1> 
   150                              <1> PORTB		EQU	061h
   151                              <1> REFRESH_STATUS	EQU	010h	; Refresh signal status
   152                              <1> 
   153                              <1> ; AC97 Codec registers.
   154                              <1> 
   155                              <1> ; 22/07/2020
   156                              <1> ; REALTEK ALC655 and ADI SOUNDMAX AD1980 CODEC MIXER REGISTERS
   157                              <1> 
   158                              <1> ; each codec/mixer register is 16bits
   159                              <1> 
   160                              <1> CODEC_RESET_REG                 equ     00h	; reset codec
   161                              <1> CODEC_MASTER_VOL_REG            equ     02h	; master volume
   162                              <1> CODEC_HP_VOL_REG                equ     04h	; headphone volume ; AD1980
   163                              <1> CODEC_MASTER_MONO_VOL_REG       equ     06h	; master mono volume (mono-out)
   164                              <1> ;CODEC_MASTER_TONE_REG          equ     08h	; master tone (R+L) ; (not used)
   165                              <1> CODEC_PCBEEP_VOL_REG            equ     0Ah	; PC beep volume ; ALC655
   166                              <1> CODEC_PHONE_VOL_REG             equ     0Ch	; phone volume
   167                              <1> CODEC_MIC_VOL_REG               equ     0Eh	; mic volume
   168                              <1> CODEC_LINE_IN_VOL_REG           equ     10h	; line in volume
   169                              <1> CODEC_CD_VOL_REG                equ     12h	; CD volume
   170                              <1> ;CODEC_VID_VOL_REG              equ     14h	; video volume ; (not used)
   171                              <1> CODEC_AUX_VOL_REG               equ     16h	; aux volume
   172                              <1> CODEC_PCM_OUT_REG               equ     18h	; PCM out volume
   173                              <1> CODEC_RECORD_SELECT_REG         equ     1Ah	; record select
   174                              <1> CODEC_RECORD_VOL_REG            equ     1Ch	; record volume (record gain)
   175                              <1> ;CODEC_RECORD_MIC_VOL_REG       equ     1Eh	; record mic volume ; (not used)
   176                              <1> CODEC_GP_REG                    equ     20h	; general purpose
   177                              <1> ;CODEC_3D_CONTROL_REG           equ     22h	; 3D control
   178                              <1> ;;CODEC_AUDIO_INT_PAGING_REG    equ	24h	; audio int & paging ; (not used) 
   179                              <1> CODEC_POWER_CTRL_REG            equ     26h	; power down control
   180                              <1> CODEC_EXT_AUDIO_REG             equ     28h	; extended audio ID
   181                              <1> CODEC_EXT_AUDIO_CTRL_REG        equ     2Ah	; extended audio status/control
   182                              <1> CODEC_PCM_FRONT_DACRATE_REG     equ     2Ch	; PCM front sample rate
   183                              <1> CODEC_PCM_SURND_DACRATE_REG     equ     2Eh	; PCM surround sample rate
   184                              <1> CODEC_PCM_LFE_DACRATE_REG       equ     30h	; PCM Center/LFE sample rate
   185                              <1> CODEC_LR_ADCRATE_REG            equ     32h	; PCM input sample rate
   186                              <1> CODEC_MIC_ADCRATE_REG           equ     34h	; mic in sample rate  ; AD1980
   187                              <1> CODEC_PCM_LFE_VOL_REG           equ     36h	; PCM Center/LFE volume
   188                              <1> CODEC_PCM_SURND_VOL_REG         equ     38h	; PCM surround volume
   189                              <1> ;CODEC_SPDIF_CTRL_REG           equ     3Ah	; S/PDIF control
   190                              <1> ; 22/07/2020
   191                              <1> CODEC_MISC_CRTL_BITS_REG	equ	76h	; misc control bits ; AD1980
   192                              <1> ;	
   193                              <1> CODEC_VENDOR_ID1		equ	7Ch	; REALTEK: 414Ch, ADI: 4144h	
   194                              <1> CODEC_VENDOR_ID2		equ	7Eh	; REALTEK: 4760h, ADI: 5370h	
   195                              <1> 
   196                              <1> ; VT8233 SGD bits (21/04/2017)
   197                              <1> FLAG	EQU BIT30
   198                              <1> EOL	EQU BIT31
   199                              <1> 
   200                              <1> ; INTEL ICH EQUATES
   201                              <1> ; 28/05/2017
   202                              <1> INTEL_VID	equ	8086h	; Intel's PCI vendor ID
   203                              <1> ICH_DID		equ	2415h	; ICH (82801AA) device ID
   204                              <1> NAMBAR_REG      equ	10h	; native audio mixer Base Address Register
   205                              <1> NABMBAR_REG     equ	14h	; native audio bus mastering Base Addr Reg
   206                              <1> 
   207                              <1> PI_CR_REG       equ     0Bh     ; PCM in Control Register
   208                              <1> PO_CR_REG	equ     1Bh     ; PCM out Control Register
   209                              <1> MC_CR_REG	equ     2Bh     ; MIC in Control Register
   210                              <1> 
   211                              <1> PI_SR_REG	equ     6       ; PCM in Status register
   212                              <1> PO_SR_REG	equ     16h     ; PCM out Status register
   213                              <1> MC_SR_REG	equ     26h     ; MIC in Status register
   214                              <1> 
   215                              <1> IOCE 		equ     BIT4    ; interrupt on complete enable.
   216                              <1> FEIFE		equ     BIT3    ; set if you want an interrupt to fire
   217                              <1> LVBIE		equ     BIT2    ; last valid buffer interrupt enable.
   218                              <1> RR 		equ     BIT1    ; reset registers. Nukes all regs
   219                              <1>                                 ; except bits 4:2 of this register.
   220                              <1>                                 ; Only set this bit if BIT 0 is 0
   221                              <1> RPBM		equ     BIT0    ; Run/Pause
   222                              <1> 				; set this bit to start the codec!
   223                              <1> 
   224                              <1> PI_BDBAR_REG	equ     0       ; PCM in buffer descriptor BAR
   225                              <1> PO_BDBAR_REG	equ     10h     ; PCM out buffer descriptor BAR
   226                              <1> MC_BDBAR_REG	equ     20h     ; MIC in buffer descriptor BAR
   227                              <1> 
   228                              <1> PI_CIV_REG	equ     4       ; PCM in current Index value (RO)
   229                              <1> PO_CIV_REG	equ     14h     ; PCM out current Index value (RO)
   230                              <1> MC_CIV_REG 	equ     24h     ; MIC in current Index value (RO)
   231                              <1> 
   232                              <1> PI_LVI_REG	equ     5       ; PCM in Last Valid Index
   233                              <1> PO_LVI_REG	equ     15h     ; PCM out Last Valid Index
   234                              <1> MC_LVI_REG	equ     25h     ; MIC in Last Valid Index
   235                              <1> 
   236                              <1> IOC		equ     BIT31	; Fire an interrupt whenever this
   237                              <1>                 		; buffer is complete.
   238                              <1> BUP		equ     BIT30	; Buffer Underrun Policy.
   239                              <1> 
   240                              <1> GLOB_CNT_REG	equ     2Ch     ; Global Control Register
   241                              <1> GLOB_STS_REG	equ     30h     ; Global Status register (RO)
   242                              <1> 
   243                              <1> CTRL_ST_CREADY	equ   BIT8+BIT9+BIT28 ; Primary Codec Ready
   244                              <1> 
   245                              <1> CODEC_REG_POWERDOWN   equ 26h
   246                              <1> CODEC_REG_ST          equ 26h
   247                              <1> 
   248                              <1> ; 22/06/2017
   249                              <1> PO_PICB_REG	equ 18h	; PCM Out Position In Current Buffer Register
   250                              <1> 
   251                              <1> ;=============================================================================
   252                              <1> ;               CODE
   253                              <1> ;=============================================================================
   254                              <1> 
   255                              <1> ; CODE for INTEL ICH AC'97 AUDIO CONTROLLER
   256                              <1> 
   257                              <1> DetectICH:
   258                              <1> 	; 10/06/2017
   259                              <1> 	; 05/06/2017
   260                              <1> 	; 29/05/2017
   261                              <1> 	; 28/05/2017
   262 00011FAF B886801524          <1> 	mov     eax, (ICH_DID << 16) + INTEL_VID
   263 00011FB4 E876000000          <1>         call    pciFindDevice
   264 00011FB9 730D                <1>         jnc     short d_ac97_1
   265                              <1> d_ac97_0:
   266                              <1> ; couldn't find the audio device!
   267 00011FBB C3                  <1> 	retn
   268                              <1> 
   269                              <1> ; CODE for VIA VT8233 AUDIO CONTROLLER
   270                              <1> 
   271                              <1> DetectVT8233:
   272                              <1> 	; 10/06/2017
   273                              <1> 	; 05/06/2017
   274                              <1> 	; 29/05/2017
   275                              <1> 	; 03/04/2017
   276 00011FBC B806115930          <1> 	mov     eax, (VT8233_DID << 16) + VIA_VID
   277 00011FC1 E869000000          <1>         call    pciFindDevice
   278                              <1> ;       jnc     short d_vt8233_0
   279                              <1> ; couldn't find the audio device!
   280                              <1> ;	retn
   281 00011FC6 72F3                <1> 	jc	short d_ac97_0  ; 28/05/2017
   282                              <1> d_vt8233_0:
   283                              <1> 	; 24/03/2017 ('player.asm')
   284                              <1> 	; 12/11/2016 
   285                              <1> 	; Erdogan Tan - 8/11/2016
   286                              <1> 	; References: Kolibrios - vt823x.asm (2016)
   287                              <1> 	;	      VIA VT8235 V-Link South Bridge (VT8235-VIA.PDF)(2002)
   288                              <1> 	;	      lowlevel.eu - AC97 (2016)
   289                              <1> 	;	      .wav player for DOS by Jeff Leyda (2002) -this file-
   290                              <1> 	;	      Linux kernel - via82xx.c (2016)
   291                              <1> d_ac97_1:
   292                              <1> 	; eax = BUS/DEV/FN
   293                              <1> 	;	00000000BBBBBBBBDDDDDFFF00000000
   294                              <1> 	; edx = DEV/VENDOR
   295                              <1> 	;	DDDDDDDDDDDDDDDDVVVVVVVVVVVVVVVV
   296                              <1> 
   297 00011FC8 A3[08710100]        <1> 	mov	[audio_dev_id], eax
   298 00011FCD 8915[0C710100]      <1> 	mov	[audio_vendor], edx
   299                              <1> 
   300                              <1> 	; init controller
   301 00011FD3 B004                <1> 	mov	al, PCI_CMD_REG ; command register (04h)
   302 00011FD5 E8E2000000          <1> 	call	pciRegRead32
   303                              <1> 
   304                              <1> 	; eax = BUS/DEV/FN/REG
   305                              <1> 	; edx = STATUS/COMMAND
   306                              <1> 	; 	SSSSSSSSSSSSSSSSCCCCCCCCCCCCCCCC
   307 00011FDA 8915[10710100]      <1> 	mov	[audio_stats_cmd], edx
   308                              <1> 
   309 00011FE0 B010                <1> 	mov	al, PCI_IO_BASE ; IO base address register (10h)
   310                              <1> 	;mov	al, NAMBAR_REG	; Native Audio Mixer BAR (10h)
   311 00011FE2 E8D5000000          <1> 	call	pciRegRead32
   312                              <1> 
   313 00011FE7 66813D[0C710100]86- <1> 	cmp	word [audio_vendor], 8086h ; AC'97 ?
   313 00011FEF 80                  <1>
   314 00011FF0 751F                <1> 	jne	short d_vt8233_1
   315                              <1> 
   316 00011FF2 6683E2FE            <1> 	and	dx, 0FFFEh ; Audio Codec IO_ADDR_MASK
   317 00011FF6 668915[38710100]    <1> 	mov	[NAMBAR], dx
   318                              <1> 
   319 00011FFD B014                <1> 	mov	al, NABMBAR_REG ; Native Audio Bus Mastering BAR (14h)
   320 00011FFF E8B8000000          <1> 	call	pciRegRead32	
   321                              <1> 
   322 00012004 6683E2C0            <1> 	and	dx, 0FFC0h ; Audio Controller IO_ADDR_MASK
   323 00012008 668915[3A710100]    <1> 	mov	[NABMBAR], dx
   324                              <1>         ;mov	[audio_io_base], dx
   325                              <1> 	
   326 0001200F EB0B                <1> 	jmp	short d_ac97_2
   327                              <1> 
   328                              <1> d_vt8233_1:
   329 00012011 6683E2C0            <1> 	and     dx, 0FFC0h ; Audio Controller IO_ADDR_MASK 
   330 00012015 668915[06710100]    <1>         mov     [audio_io_base], dx
   331                              <1> 
   332                              <1> d_ac97_2:
   333                              <1> 	; 10/06/2017
   334 0001201C B03C                <1> 	mov	al, AC97_INT_LINE ; Interrupt Line Register (3Ch)
   335                              <1> 	;call	pciRegRead32
   336 0001201E E886000000          <1> 	call	pciRegRead8
   337                              <1> 
   338                              <1> 	;and 	edx, 0FFh
   339 00012023 6681E2FF00          <1> 	and	dx, 0FFh
   340                              <1> 
   341 00012028 8815[03710100]      <1>   	mov     [audio_intr], dl
   342                              <1> 
   343 0001202E C3                  <1> 	retn
   344                              <1> 
   345                              <1> 	;; (Note: Interrupts are already enabled by TRDOS 386 kernel!)
   346                              <1> 	;mov	cx, dx
   347                              <1> 	
   348                              <1> 	;in	al, 0A1h ; irq 8-15
   349                              <1> 	;mov	ah, al
   350                              <1> 	;in	al, 21h  ; irq 0-7 
   351                              <1> 	;btr	ax, dx	 ; unmask ; 17/03/2017
   352                              <1> 	;;bts	ax, dx   ; MASK interrupt ; 10/06/2017 
   353                              <1> 	;out	21h, al  ; irq <= 7
   354                              <1> 	;mov	al, ah
   355                              <1> 	;out	0A1h, al ; irq > 7
   356                              <1> 	;
   357                              <1> 	
   358                              <1> 	; 10/06/2017
   359                              <1> 	; === Intel ICH I/O Controller Hub Datasheet, Section 8.1.16 ===
   360                              <1> 	; PRQ[n]_ROUT Register (61h, PRQB) Bit 7:
   361                              <1> 	; Interrupt Routing Enable (IRQEN).
   362                              <1> 	; 0 = The corresponding PIRQ is routed to one of the ISA-compatible
   363                              <1> 	;     interrupts specified in bits[3:0].
   364                              <1> 	; 1 = The PIRQ is not routed to the 8259.
   365                              <1> 	; Note: If the PIRQ is intended to cause an interrupt to the ICHs 
   366                              <1> 	;	integrated I/O APIC, then this bit should be set to 0 and 
   367                              <1> 	;	the APIC_EN bit should be set to 1. 
   368                              <1> 	;	The IRQEN must be set to 0 and the PIRQ routed to 
   369                              <1> 	;	an 8259 interrupt via the IRQ Routing filed (bits[3:0).
   370                              <1> 	;	The corresponding 8259 interrupt must be masked via the 
   371                              <1> 	;	appropriated bit in the 8259s OCW1 (Interrupt Mask)
   372                              <1> 	;	register. The IOAPIC must then be enabled by setting 
   373                              <1> 	;	the APIC_EN bit in the GEN_CNTL register.
   374                              <1> 
   375                              <1> 	;mov	eax, 0F861h  ; D31:F0
   376                              <1> 		;AL=61h : PIRQ[B] Routing Control Reg, LPC interface
   377                              <1> 	;;mov	dl, [audio_intr]
   378                              <1> 	;call	pciRegWrite8
   379                              <1> 	;;mov	al, 0D0h ; General Control Register (GEN_CTL)
   380                              <1> 	;;call	pciRegRead32
   381                              <1> 	;;or	edx, 100h ; Bit 8, APIC_EN (Enable I/O APIC) 
   382                              <1> 	;;;call	pciRegWrite32
   383                              <1> 	;;and	edx, ~100h
   384                              <1> 	;;call	pciRegWrite32 ; ; Bit 8, APIC_EN (Disable I/O APIC) 
   385                              <1> 	;
   386                              <1> 
   387                              <1> 	;mov	dx, 4D1h	; 8259 ELCR2
   388                              <1>     	;in	al, dx
   389                              <1> 	;mov	ah, al
   390                              <1> 	;;mov	dx, 4D0h 	; 8259 ELCR1
   391                              <1> 	;dec	dl
   392                              <1> 	;in	al, dx
   393                              <1> 	;bts	ax, cx
   394                              <1> 	;;mov	dx, 4D0h
   395                              <1> 	;out	dx, al		; set level-triggered mode
   396                              <1> 	;mov	al, ah ; 29/05/2017
   397                              <1> 	;;mov	dx, 4D1h
   398                              <1> 	;inc	dl
   399                              <1> 	;out	dx, al		; set level-triggered mode
   400                              <1> 
   401                              <1> 	;xor	eax, eax ; 0
   402                              <1> 
   403                              <1> 	;retn
   404                              <1> 
   405                              <1> ; CODE for PCI
   406                              <1> 
   407                              <1> pciFindDevice:
   408                              <1> 	; 03/04/2017 ('pci.asm', 20/03/2017)
   409                              <1> 	;
   410                              <1> 	; scan through PCI space looking for a device+vendor ID
   411                              <1> 	;
   412                              <1> 	; Entry: EAX=Device+Vendor ID
   413                              <1> 	;
   414                              <1> 	; Exit: EAX=PCI address if device found
   415                              <1> 	;	 EDX=Device+Vendor ID
   416                              <1> 	;        CY clear if found, set if not found. EAX invalid if CY set.
   417                              <1> 	;
   418                              <1> 	; Destroys: ebx, esi, edi, cl
   419                              <1> 	;
   420                              <1> 
   421                              <1> 	;push	ecx
   422 0001202F 50                  <1> 	push	eax
   423                              <1> 	;push	esi
   424                              <1> 	;push	edi
   425                              <1> 
   426 00012030 89C6                <1>         mov     esi, eax                ; save off vend+device ID
   427 00012032 BF00FFFF7F          <1>         mov     edi, (80000000h - 100h) ; start with bus 0, dev 0 func 0
   428                              <1> 
   429                              <1> nextPCIdevice:
   430 00012037 81C700010000        <1>         add     edi, 100h
   431 0001203D 81FF00F8FF80        <1>         cmp     edi, 80FFF800h		; scanned all devices?
   432 00012043 F9                  <1>         stc
   433 00012044 740C                <1>         je      short PCIScanExit       ; not found
   434                              <1> 
   435 00012046 89F8                <1>         mov     eax, edi                ; read PCI registers
   436 00012048 E86F000000          <1>         call    pciRegRead32
   437 0001204D 39F2                <1>         cmp     edx, esi                ; found device?
   438 0001204F 75E6                <1>         jne     short nextPCIdevice
   439 00012051 F8                  <1>         clc
   440                              <1> 
   441                              <1> PCIScanExit:
   442 00012052 9C                  <1> 	pushf
   443 00012053 B8FFFFFF7F          <1> 	mov	eax, NOT_BIT31 	; 19/03/2017
   444 00012058 21F8                <1> 	and	eax, edi	; return only bus/dev/fn #
   445 0001205A 9D                  <1> 	popf
   446                              <1> 
   447                              <1> 	;pop	edi
   448                              <1> 	;pop	esi
   449 0001205B 5A                  <1> 	pop	edx
   450                              <1> 	;pop	ecx
   451 0001205C C3                  <1> 	retn
   452                              <1> 
   453                              <1> pciRegRead:
   454                              <1> 	; 03/04/2017 ('pci.asm', 20/03/2017)
   455                              <1> 	;
   456                              <1> 	; 8/16/32bit PCI reader
   457                              <1> 	;
   458                              <1> 	; Entry: EAX=PCI Bus/Device/fn/register number
   459                              <1> 	;           BIT30 set if 32 bit access requested
   460                              <1> 	;           BIT29 set if 16 bit access requested
   461                              <1> 	;           otherwise defaults to 8 bit read
   462                              <1> 	;
   463                              <1> 	; Exit:  DL,DX,EDX register data depending on requested read size
   464                              <1> 	;
   465                              <1> 	; Note1: this routine is meant to be called via pciRegRead8,
   466                              <1> 	;	 pciRegread16 or pciRegRead32, listed below.
   467                              <1> 	;
   468                              <1> 	; Note2: don't attempt to read 32 bits of data from a non dword
   469                              <1> 	;	 aligned reg number. Likewise, don't do 16 bit reads from
   470                              <1> 	;	 non word aligned reg #
   471                              <1> 	
   472 0001205D 53                  <1> 	push	ebx
   473 0001205E 51                  <1> 	push	ecx
   474 0001205F 89C3                <1>         mov     ebx, eax		; save eax, dh
   475 00012061 88F1                <1>         mov     cl, dh
   476                              <1> 
   477 00012063 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; clear out data size request
   478 00012068 0D00000080          <1>         or      eax, BIT31		; make a PCI access request
   479 0001206D 24FC                <1>         and     al, ~3 ; NOT 3		; force index to be dword
   480                              <1> 
   481 0001206F 66BAF80C            <1>         mov     dx, PCI_INDEX_PORT
   482 00012073 EF                  <1>         out	dx, eax			; write PCI selector
   483                              <1> 	
   484 00012074 66BAFC0C            <1>         mov     dx, PCI_DATA_PORT
   485 00012078 88D8                <1>         mov     al, bl
   486 0001207A 2403                <1>         and     al, 3			; figure out which port to
   487 0001207C 00C2                <1>         add     dl, al			; read to
   488                              <1> 
   489 0001207E F7C3000000C0        <1> 	test    ebx, PCI32+PCI16
   490 00012084 7507                <1>         jnz     short _pregr0
   491 00012086 EC                  <1> 	in	al, dx			; return 8 bits of data
   492 00012087 88C2                <1>         mov	dl, al
   493 00012089 88CE                <1> 	mov     dh, cl			; restore dh for 8 bit read
   494 0001208B EB12                <1> 	jmp	short _pregr2
   495                              <1> _pregr0:	
   496 0001208D F7C300000080        <1> 	test    ebx, PCI32
   497 00012093 7507                <1>         jnz	short _pregr1
   498 00012095 66ED                <1> 	in	ax, dx
   499 00012097 6689C2              <1>         mov     dx, ax			; return 16 bits of data
   500 0001209A EB03                <1> 	jmp	short _pregr2
   501                              <1> _pregr1:
   502 0001209C ED                  <1> 	in	eax, dx			; return 32 bits of data
   503 0001209D 89C2                <1> 	mov	edx, eax
   504                              <1> _pregr2:
   505 0001209F 89D8                <1> 	mov     eax, ebx		; restore eax
   506 000120A1 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; clear out data size request
   507 000120A6 59                  <1> 	pop	ecx
   508 000120A7 5B                  <1> 	pop	ebx
   509 000120A8 C3                  <1> 	retn
   510                              <1> 
   511                              <1> pciRegRead8:
   512 000120A9 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 8 bit read size
   513 000120AE EBAD                <1>         jmp     short pciRegRead	; call generic PCI access
   514                              <1> 
   515                              <1> pciRegRead16:
   516 000120B0 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 16 bit read size
   517 000120B5 0D00000040          <1>         or      eax, PCI16		; call generic PCI access
   518 000120BA EBA1                <1>         jmp     short pciRegRead
   519                              <1> 
   520                              <1> pciRegRead32:
   521 000120BC 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 32 bit read size
   522 000120C1 0D00000080          <1>         or      eax, PCI32		; call generic PCI access
   523 000120C6 EB95                <1>         jmp     pciRegRead
   524                              <1> 
   525                              <1> pciRegWrite:
   526                              <1> 	; 03/04/2017 ('pci.asm', 29/11/2016)
   527                              <1> 	;
   528                              <1> 	; 8/16/32bit PCI writer
   529                              <1> 	;
   530                              <1> 	; Entry: EAX=PCI Bus/Device/fn/register number
   531                              <1> 	;           BIT31 set if 32 bit access requested
   532                              <1> 	;           BIT30 set if 16 bit access requested
   533                              <1> 	;           otherwise defaults to 8bit read
   534                              <1> 	;        DL/DX/EDX data to write depending on size
   535                              <1> 	;
   536                              <1> 	; Note1: this routine is meant to be called via pciRegWrite8, 
   537                              <1> 	;	 pciRegWrite16 or pciRegWrite32 as detailed below.
   538                              <1> 	;
   539                              <1> 	; Note2: don't attempt to write 32bits of data from a non dword
   540                              <1> 	;	 aligned reg number. Likewise, don't do 16 bit writes from
   541                              <1> 	;	 non word aligned reg #
   542                              <1> 
   543 000120C8 53                  <1> 	push	ebx
   544 000120C9 51                  <1> 	push	ecx
   545 000120CA 89C3                <1>         mov     ebx, eax		; save eax, edx
   546 000120CC 89D1                <1>         mov     ecx, edx
   547 000120CE 25FFFFFF3F          <1> 	and     eax, NOT_PCI32_PCI16	; clear out data size request
   548 000120D3 0D00000080          <1>         or      eax, BIT31		; make a PCI access request
   549 000120D8 24FC                <1>         and     al, ~3 ; NOT 3		; force index to be dword
   550                              <1> 
   551 000120DA 66BAF80C            <1>         mov     dx, PCI_INDEX_PORT
   552 000120DE EF                  <1>         out	dx, eax			; write PCI selector
   553                              <1> 	
   554 000120DF 66BAFC0C            <1>         mov     dx, PCI_DATA_PORT
   555 000120E3 88D8                <1>         mov     al, bl
   556 000120E5 2403                <1>         and     al, 3			; figure out which port to
   557 000120E7 00C2                <1>         add     dl, al			; write to
   558                              <1> 
   559 000120E9 F7C3000000C0        <1> 	test    ebx, PCI32+PCI16
   560 000120EF 7505                <1>         jnz     short _pregw0
   561 000120F1 88C8                <1> 	mov	al, cl 			; put data into al
   562 000120F3 EE                  <1> 	out	dx, al
   563 000120F4 EB12                <1> 	jmp	short _pregw2
   564                              <1> _pregw0:
   565 000120F6 F7C300000080        <1> 	test    ebx, PCI32
   566 000120FC 7507                <1>         jnz     short _pregw1
   567 000120FE 6689C8              <1> 	mov	ax, cx			; put data into ax
   568 00012101 66EF                <1> 	out	dx, ax
   569 00012103 EB03                <1> 	jmp	short _pregw2
   570                              <1> _pregw1:
   571 00012105 89C8                <1> 	mov	eax, ecx		; put data into eax 		
   572 00012107 EF                  <1> 	out	dx, eax
   573                              <1> _pregw2:
   574 00012108 89D8                <1>         mov     eax, ebx		; restore eax
   575 0001210A 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; clear out data size request
   576 0001210F 89CA                <1>         mov     edx, ecx		; restore dx
   577 00012111 59                  <1> 	pop	ecx
   578 00012112 5B                  <1> 	pop	ebx
   579 00012113 C3                  <1> 	retn
   580                              <1> 
   581                              <1> pciRegWrite8:
   582 00012114 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 8 bit write size
   583 00012119 EBAD                <1>         jmp	short pciRegWrite	; call generic PCI access
   584                              <1> 
   585                              <1> pciRegWrite16:
   586 0001211B 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 16 bit write size
   587 00012120 0D00000040          <1>         or      eax, PCI16		; call generic PCI access
   588 00012125 EBA1                <1>         jmp	short pciRegWrite
   589                              <1> 
   590                              <1> pciRegWrite32:
   591 00012127 25FFFFFF3F          <1>         and     eax, NOT_PCI32_PCI16	; set up 32 bit write size
   592 0001212C 0D00000080          <1>         or      eax, PCI32		; call generic PCI access
   593 00012131 EB95                <1>         jmp	pciRegWrite
   594                              <1> 
   595                              <1> init_codec:
   596                              <1> 	; 05/06/2017
   597                              <1> 	; 28/05/2017 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   598                              <1> 	;
   599 00012133 A1[08710100]        <1> 	mov	eax, [audio_dev_id]	
   600 00012138 B041                <1> 	mov	al, VIA_ACLINK_CTRL
   601 0001213A E86AFFFFFF          <1> 	call	pciRegRead8
   602                              <1> 	; ?
   603 0001213F B040                <1> 	mov	al, VIA_ACLINK_STAT
   604 00012141 E863FFFFFF          <1> 	call	pciRegRead8
   605 00012146 F6C201              <1> 	test	dl, VIA_ACLINK_C00_READY
   606 00012149 7508                <1>         jnz     short _codec_ready_1
   607 0001214B E80E000000          <1> 	call	reset_codec
   608 00012150 7306                <1> 	jnc	short _codec_ready_2 ; eax = 1
   609 00012152 C3                  <1> 	retn
   610                              <1> _codec_ready_1:
   611 00012153 B801000000          <1> 	mov	eax, 1
   612                              <1> _codec_ready_2:
   613 00012158 E886000000          <1> 	call	codec_io_w16
   614                              <1> detect_codec:
   615 0001215D C3                  <1> 	retn
   616                              <1> 
   617                              <1> reset_codec:
   618                              <1> 	; 16/04/2017
   619                              <1> 	; 23/03/2017 
   620                              <1> 	; ('codec.asm')
   621                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   622 0001215E A1[08710100]        <1> 	mov	eax, [audio_dev_id]
   623 00012163 B041                <1>  	mov	al, VIA_ACLINK_CTRL
   624 00012165 B2E0                <1>        	mov	dl, VIA_ACLINK_CTRL_ENABLE + VIA_ACLINK_CTRL_RESET + VIA_ACLINK_CTRL_SYNC
   625 00012167 E8A8FFFFFF          <1> 	call	pciRegWrite8
   626                              <1> 
   627 0001216C E849000000          <1> 	call	delay_100ms 	; wait 100 ms
   628                              <1> _rc_cold:
   629 00012171 E814000000          <1>         call    cold_reset
   630 00012176 7301                <1>         jnc     short _reset_codec_ok
   631                              <1> 	
   632                              <1> 	; 16/04/2017
   633                              <1>         ;xor     eax, eax         ; timeout error
   634                              <1>        	;stc
   635 00012178 C3                  <1> 	retn
   636                              <1> 
   637                              <1> _reset_codec_ok:
   638                              <1> 	; 01/09/2020
   639                              <1> 	; 15/08/2020
   640                              <1> 	; 27/07/2020
   641                              <1> 	; also reset codec by using index control register 0 of AD1980 or ALC655
   642                              <1> 	; (to fix line out -2 channels audio playing- problem on AD1980 codec)  
   643                              <1> 
   644 00012179 29C0                <1> 	sub	eax, eax
   645 0001217B BA00000000          <1> 	mov	edx, CODEC_RESET_REG ; 00h ; Reset register
   646 00012180 E8CA000000          <1> 	call	codec_write
   647                              <1> 
   648                              <1> 	;sub	eax, eax
   649                              <1> 	; 01/09/2020
   650                              <1> 	; 15/08/2020
   651                              <1> 	; AD1980 BugFix
   652                              <1> 	; (set HPSEL -headphone amp to be driven from mixer- and
   653                              <1> 	;      CLDIS - center and LFE disable- bits)	
   654                              <1> 	;mov	eax, 0C00h ; HPSEL = bit 10, CLDIS = bit 11 ; 01/09/2020
   655                              <1>  	;mov	edx, CODEC_MISC_CRTL_BITS_REG ; 76h ; Misc Ctrl Bits ; AD1980
   656                              <1> 	;call	codec_write
   657                              <1> 
   658 00012185 31C0                <1>         xor     eax, eax
   659                              <1>         ;mov	al, VIA_ACLINK_C00_READY ; 1
   660 00012187 FEC0                <1>         inc	al
   661 00012189 C3                  <1> 	retn
   662                              <1> 
   663                              <1> cold_reset:
   664                              <1> 	; 16/04/2017
   665                              <1> 	; 23/03/2017
   666                              <1> 	; ('codec.asm')
   667                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   668                              <1> 	;mov	eax, [audio_dev_id]
   669                              <1> 	;mov	al, VIA_ACLINK_CTRL
   670 0001218A 30D2                <1> 	xor	dl, dl ; 0
   671 0001218C E883FFFFFF          <1> 	call	pciRegWrite8
   672                              <1> 
   673 00012191 E824000000          <1> 	call	delay_100ms 	; wait 100 ms
   674                              <1> 
   675                              <1> 	;; ACLink on, deassert ACLink reset, VSR, SGD data out
   676                              <1>         ;; note - FM data out has trouble with non VRA codecs !!
   677                              <1>         
   678                              <1> 	;mov	eax, [audio_dev_id]
   679                              <1> 	;mov	al, VIA_ACLINK_CTRL
   680 00012196 B2CC                <1> 	mov	dl, VIA_ACLINK_CTRL_INIT
   681 00012198 E877FFFFFF          <1> 	call	pciRegWrite8
   682                              <1> 
   683 0001219D B910000000          <1> 	mov	ecx, 16	; total 2s
   684                              <1> 
   685                              <1> _crst_wait:
   686                              <1> 	;mov	eax, [audio_dev_id]
   687 000121A2 B040                <1> 	mov	al, VIA_ACLINK_STAT
   688 000121A4 E800FFFFFF          <1> 	call	pciRegRead8	
   689                              <1> 
   690 000121A9 F6C201              <1>         test    dl, VIA_ACLINK_C00_READY
   691 000121AC 750B                <1>         jnz     short _crst_ok
   692                              <1> 
   693 000121AE 51                  <1> 	push	ecx
   694 000121AF E806000000          <1> 	call	delay_100ms
   695 000121B4 59                  <1> 	pop	ecx
   696                              <1> 
   697 000121B5 49                  <1>         dec     ecx
   698 000121B6 75EA                <1>         jnz     short _crst_wait
   699                              <1> 
   700                              <1> _crst_fail:
   701 000121B8 F9                  <1>         stc
   702                              <1> _crst_ok:
   703 000121B9 C3                  <1> 	retn
   704                              <1> 
   705                              <1> delay_100ms:
   706                              <1> 	; 29/05/2017
   707                              <1> 	; 24/03/2017 ('codec.asm')
   708                              <1> 	; wait 100 ms
   709 000121BA B990010000          <1> 	mov	ecx, 400  ; 400*0.25ms
   710                              <1> _delay_x_ms:
   711 000121BF E803000000          <1> 	call	delay1_4ms
   712 000121C4 E2F9                <1>         loop	_delay_x_ms
   713 000121C6 C3                  <1> 	retn
   714                              <1> 
   715                              <1> ;       delay1_4ms - Delay for 1/4 millisecond.
   716                              <1> ;	    1mS = 1000us
   717                              <1> ;       Entry:
   718                              <1> ;         None
   719                              <1> ;       Exit:
   720                              <1> ;	  None
   721                              <1> ;
   722                              <1> ;       Modified:
   723                              <1> ;         None
   724                              <1> ;
   725                              <1> 
   726                              <1> 	; 29/05/2017
   727                              <1> 	; 23/04/2017
   728                              <1> 	; 05/03/2017 (TRDOS 386)
   729                              <1> 	; ('UTILS.ASM')
   730                              <1> delay1_4ms:
   731 000121C7 50                  <1>         push    eax 
   732 000121C8 51                  <1>         push    ecx
   733 000121C9 B110                <1>         mov	cl, 16		; close enough.
   734                              <1> 
   735 000121CB E461                <1> 	in	al, PORTB ; 61h
   736                              <1> 		
   737 000121CD 2410                <1> 	and	al, REFRESH_STATUS ; 10h
   738 000121CF 88C5                <1> 	mov	ch, al		; Start toggle state
   739                              <1> _d4ms1:	
   740 000121D1 E461                <1> 	in	al, PORTB	; Read system control port
   741                              <1> 	
   742 000121D3 2410                <1> 	and	al, REFRESH_STATUS ; Refresh toggles 15.085 microseconds
   743 000121D5 38C5                <1> 	cmp	ch, al
   744 000121D7 74F8                <1> 	je	short _d4ms1	; Wait for state change
   745                              <1> 
   746 000121D9 88C5                <1> 	mov	ch, al		; Update with new state
   747 000121DB FEC9                <1> 	dec	cl
   748 000121DD 75F2                <1> 	jnz	short _d4ms1
   749                              <1> 
   750 000121DF F8                  <1> 	clc	; 29/05/2017
   751                              <1> 
   752 000121E0 59                  <1>         pop     ecx
   753 000121E1 58                  <1>         pop     eax
   754 000121E2 C3                  <1>         retn
   755                              <1> 
   756                              <1> ; 10/04/2017 (TRDOS 386)
   757                              <1> ; 12/11/2016
   758                              <1> 
   759                              <1> codec_io_w16: ;w32
   760                              <1> 	; ('codec.asm')
   761 000121E3 668B15[06710100]    <1>         mov	dx, [audio_io_base]
   762 000121EA 6681C28000          <1>         add     dx, VIA_REG_AC97
   763 000121EF EF                  <1> 	out	dx, eax
   764 000121F0 C3                  <1>         retn
   765                              <1> 
   766                              <1> codec_io_r16: ;r32
   767                              <1> 	; ('codec.asm')
   768 000121F1 668B15[06710100]    <1>         mov     dx, [audio_io_base]
   769 000121F8 6681C28000          <1>         add     dx, VIA_REG_AC97
   770 000121FD ED                  <1>         in	eax, dx
   771 000121FE C3                  <1>         retn
   772                              <1> 
   773                              <1> ctrl_io_w8:
   774                              <1> 	; ('codec.asm')
   775 000121FF 660315[06710100]    <1>         add     dx, [audio_io_base]
   776 00012206 EE                  <1>         out	dx, al
   777 00012207 C3                  <1>         retn
   778                              <1> 
   779                              <1> ctrl_io_r8:
   780                              <1> 	; ('codec.asm')
   781 00012208 660315[06710100]    <1>         add     dx, [audio_io_base]
   782 0001220F EC                  <1>         in	al, dx
   783 00012210 C3                  <1>         retn
   784                              <1> 
   785                              <1> ctrl_io_w32:
   786                              <1> 	; ('codec.asm')
   787 00012211 660315[06710100]    <1>         add     dx, [audio_io_base]
   788 00012218 EF                  <1>         out	dx, eax
   789 00012219 C3                  <1>         retn
   790                              <1> 
   791                              <1> ctrl_io_r32:
   792                              <1> 	; ('codec.asm')
   793 0001221A 660315[06710100]    <1>         add	dx, [audio_io_base]
   794 00012221 ED                  <1> 	in	eax, dx
   795 00012222 C3                  <1>         retn
   796                              <1> 
   797                              <1> codec_read:
   798                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   799                              <1>         ; Use only primary codec.
   800                              <1>         ; eax = register
   801 00012223 C1E010              <1>         shl     eax, VIA_REG_AC97_CMD_SHIFT
   802 00012226 0D00008002          <1>         or      eax, VIA_REG_AC97_PRIMARY_VALID + VIA_REG_AC97_READ
   803                              <1> 
   804 0001222B E8B3FFFFFF          <1> 	call    codec_io_w16
   805                              <1> 
   806                              <1>       	; codec_valid
   807 00012230 E831000000          <1> 	call	codec_check_ready
   808 00012235 7301                <1>         jnc	short _cr_ok
   809                              <1> 
   810 00012237 C3                  <1> 	retn
   811                              <1> 
   812                              <1> _cr_ok:
   813                              <1> 	; wait 25 ms
   814 00012238 B950000000          <1> 	mov	ecx, 80 ; (100*0.25 ms)
   815                              <1> _cr_wloop:
   816 0001223D E885FFFFFF          <1> 	call	delay1_4ms
   817 00012242 E2F9                <1> 	loop	_cr_wloop
   818                              <1> 
   819 00012244 E8A8FFFFFF          <1>         call    codec_io_r16
   820 00012249 25FFFF0000          <1>         and     eax, 0FFFFh
   821 0001224E C3                  <1>         retn
   822                              <1> 
   823                              <1> codec_write:
   824                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   825                              <1>         ; Use only primary codec.
   826                              <1>         
   827                              <1> 	; eax = data (volume)
   828                              <1> 	; edx = register (mixer register)
   829                              <1> 	
   830 0001224F C1E210              <1> 	shl     edx, VIA_REG_AC97_CMD_SHIFT
   831                              <1> 
   832 00012252 C1E000              <1>         shl     eax, VIA_REG_AC97_DATA_SHIFT ; shl eax, 0
   833 00012255 09C2                <1>         or      edx, eax
   834                              <1> 
   835 00012257 B800000000          <1>         mov     eax, VIA_REG_AC97_CODEC_ID_PRIMARY
   836 0001225C C1E01E              <1>         shl     eax, VIA_REG_AC97_CODEC_ID_SHIFT
   837 0001225F 09D0                <1>         or      eax, edx
   838                              <1> 
   839 00012261 E87DFFFFFF          <1>         call    codec_io_w16
   840                              <1>         ;mov    [codec.regs+esi], ax
   841                              <1> 
   842                              <1>         ;call	codec_check_ready
   843                              <1>        	;retn
   844                              <1> 	;jmp	short _codec_check_ready	
   845                              <1> 
   846                              <1> codec_check_ready:
   847                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
   848                              <1> 
   849                              <1> _codec_check_ready:
   850 00012266 B914000000          <1> 	mov	ecx, 20	; total 2s
   851                              <1> _ccr_wait:
   852 0001226B 51                  <1> 	push	ecx
   853                              <1> 
   854 0001226C E880FFFFFF          <1>         call    codec_io_r16
   855 00012271 A900000001          <1>         test    eax, VIA_REG_AC97_BUSY
   856 00012276 740B                <1>         jz      short _ccr_ok
   857                              <1> 
   858 00012278 E83DFFFFFF          <1> 	call	delay_100ms
   859                              <1> 
   860 0001227D 59                  <1> 	pop	ecx
   861                              <1> 
   862 0001227E 49                  <1> 	dec     ecx
   863 0001227F 75EA                <1>         jnz     short _ccr_wait
   864                              <1> 
   865 00012281 F9                  <1>         stc
   866 00012282 C3                  <1>         retn
   867                              <1> 
   868                              <1> _ccr_ok:
   869 00012283 59                  <1> 	pop	ecx
   870 00012284 25FFFF0000          <1> 	and     eax, 0FFFFh
   871 00012289 C3                  <1>         retn
   872                              <1> 
   873                              <1> codec_config:
   874                              <1> 	; 10/06/2017
   875                              <1> 	; 29/05/2017
   876                              <1> 	; 24/04/2017
   877                              <1> 	; 21/04/2017
   878                              <1> 	; 16/04/2017 (TRDOS 386 Kernel) 
   879                              <1> 	; 15/11/2016 ('codec.asm', 'player.com')
   880                              <1> 	; 14/11/2016
   881                              <1> 	; 12/11/2016 - Erdogan Tan
   882                              <1> 	;	     (Ref: KolibriOS, 'setup_codec', codec.inc)
   883                              <1> 
   884 0001228A B802020000          <1> 	mov     eax, 0202h
   885 0001228F 66A3[36710100]      <1> 	mov	[audio_master_volume], ax
   886 00012295 66B81F1F            <1> 	mov	ax, 1F1Fh ; 31,31
   887 00012299 BA02000000          <1> 	mov	edx, CODEC_MASTER_VOL_REG ; 02h ; Line Out
   888 0001229E E8ACFFFFFF          <1> 	call	codec_write
   889                              <1> 	;jc	short cconfig_error
   890                              <1> 
   891                              <1>  	;mov    eax, 0202h
   892 000122A3 66B80202            <1> 	mov     ax, 0202h
   893 000122A7 BA18000000          <1> 	mov	edx, CODEC_PCM_OUT_REG ; 18h ; Wave Output (Stereo)
   894 000122AC E89EFFFFFF          <1> 	call	codec_write
   895                              <1> 	;jc	short cconfig_error
   896                              <1>       
   897                              <1>  	;mov    eax, 0202h
   898 000122B1 66B80202            <1> 	mov	ax, 0202h
   899 000122B5 BA04000000          <1> 	mov	edx, CODEC_AUX_VOL ; 04h ; CODEC_HP_VOL_REG ; HeadPhone
   900 000122BA E890FFFFFF          <1> 	call	codec_write
   901                              <1> 	;jc	short cconfig_error
   902                              <1> 
   903                              <1>  	;mov    eax, 08h
   904                              <1>         ;mov    ax,  08h
   905 000122BF 66B80880            <1> 	mov	ax, 8008h ; Mute
   906 000122C3 BA0C000000          <1> 	mov	edx, 0Ch  ; AC97_PHONE_VOL ; TAD Input (Mono)
   907 000122C8 E882FFFFFF          <1> 	call	codec_write
   908                              <1> 	;jc	short cconfig_error
   909                              <1> 
   910                              <1>  	;mov    eax, 0808h
   911 000122CD 66B80808            <1>         mov     ax,  0808h
   912 000122D1 BA10000000          <1>         mov	edx, CODEC_LINE_IN_VOL_REG ; 10h ; Line Input (Stereo)	
   913 000122D6 E874FFFFFF          <1> 	call	codec_write
   914                              <1> 	;jc	short cconfig_error
   915                              <1> 
   916                              <1>  	;mov    eax, 0808h
   917 000122DB 66B80808            <1> 	mov     ax,  0808h
   918 000122DF BA12000000          <1>         mov	edx, CODEC_CD_VOL_REG ; 12h ; CR Input (Stereo)
   919 000122E4 E866FFFFFF          <1> 	call	codec_write
   920                              <1> 	;jc	short cconfig_error
   921                              <1> 
   922                              <1>  	;mov    eax, 0808h
   923 000122E9 66B80808            <1> 	mov     ax,  0808h
   924 000122ED BA16000000          <1>         mov	edx, CODEC_AUX_VOL_REG ; 16h ; Aux Input (Stereo)
   925                              <1> 	;call	codec_write
   926                              <1> 	;;jc	short cconfig_error
   927 000122F2 E958FFFFFF          <1> 	jmp	codec_write ; 10/06/2017
   928                              <1> 
   929                              <1> ;	; Extended Audio Status (2Ah)
   930                              <1> ;	mov	eax, CODEC_EXT_AUDIO_CTRL_REG ; 2Ah 
   931                              <1> ;	call	codec_read
   932                              <1> ;	and     eax, 0FFFFh - 2		; clear DRA (BIT1)
   933                              <1> ;	;or     eax, 1			; set VRA (BIT0)
   934                              <1> ;	or	eax, 5  	; VRA (BIT0) & S/PDIF (BIT2) ; 14/11/2016
   935                              <1> ;	mov	edx, CODEC_EXT_AUDIO_CTRL_REG
   936                              <1> ;	call	codec_write
   937                              <1> ;	;jc	short cconfig_error
   938                              <1> ;
   939                              <1> ;set_sample_rate:
   940                              <1> ;	;movzx	eax, word [audio_freq]
   941                              <1> ;	mov	ax, [audio_freq]
   942                              <1> ;	mov	edx, CODEC_PCM_FRONT_DACRATE_REG ; 2Ch ; PCM Front DAC Rate
   943                              <1> ;	;call	codec_write
   944                              <1> ;	;retn
   945                              <1> ;	jmp	codec_write
   946                              <1> 	
   947                              <1> ;cconfig_error:
   948                              <1> ;	retn
   949                              <1> 
   950                              <1> vt8233_int_handler:
   951                              <1> 	; 27/07/2020
   952                              <1> 	; 22/07/2020
   953                              <1> 	; Interrupt Handler for VIA VT8237R Audio Controller
   954                              <1> 	; Note: called by 'dev_IRQ_service'
   955                              <1> 	; 14/10/2017 
   956                              <1> 	; 09/10/2017, 10/10/2017, 12/10/2017
   957                              <1> 	; 13/06/2017
   958                              <1> 	; 21/04/2017 (TRDOS 386 kernel, 'audio.s')
   959                              <1> 	; 24/03/2017 - 'PLAYER.COM' ('player.asm') 
   960                              <1> 
   961                              <1> 	;push	eax ; * must be saved !
   962                              <1> 	;push	edx
   963                              <1> 	;push	ecx
   964                              <1> 	;push	ebx ; * must be saved !
   965                              <1> 	;push	esi
   966                              <1> 	;push	edi
   967                              <1> 
   968                              <1> 	;cmp	byte [audio_busy], 1
   969                              <1> 	;jnb	short _ih0 ; 09/10/2017
   970                              <1> 
   971                              <1> 	;mov	byte [audio_flag_eol], 0
   972                              <1> 
   973 000122F7 66BA0000            <1>         mov     dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_STATUS
   974 000122FB E808FFFFFF          <1>         call    ctrl_io_r8
   975                              <1> 
   976 00012300 A880                <1> 	test    al, VIA_REG_STAT_ACTIVE
   977 00012302 7417                <1>         jz      short _ih0 ; 09/10/2017
   978                              <1> 
   979 00012304 2407                <1>         and     al, VIA_REG_STAT_EOL + VIA_REG_STAT_FLAG + VIA_REG_STAT_STOPPED
   980 00012306 A2[35710100]        <1> 	mov	[audio_flag_eol], al
   981 0001230B 740E                <1>         jz	short _ih0 ; 09/10/2017
   982                              <1> 
   983                              <1> 	; 09/10/2017
   984                              <1> 	;mov	byte [audio_busy], 1
   985                              <1> 
   986 0001230D 803D[34710100]01    <1> 	cmp	byte [audio_play_cmd], 1
   987 00012314 7315                <1> 	jnb	short _ih1 ; 10/10/2017
   988                              <1> 
   989 00012316 E84A000000          <1> 	call	channel_reset
   990                              <1> _ih0:
   991                              <1> 	; 09/10/2017
   992 0001231B A0[35710100]        <1>         mov     al, [audio_flag_eol]   ;; ack ;;
   993 00012320 66BA0000            <1>         mov     dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_STATUS
   994 00012324 E8D6FEFFFF          <1>         call    ctrl_io_w8
   995 00012329 EB39                <1> 	jmp	short _ih4
   996                              <1> _ih1:
   997                              <1> vt8233_tuneLoop:
   998 0001232B A0[35710100]        <1>         mov     al, [audio_flag_eol]   ;; ack ;;
   999 00012330 66BA0000            <1>         mov     dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_STATUS
  1000 00012334 E8C6FEFFFF          <1>         call    ctrl_io_w8
  1001                              <1> 
  1002                              <1> 	; 22/07/2020
  1003                              <1> 	;; 12/10/2017
  1004                              <1> 	;mov	byte [audio_flag], 0 ; Reset	
  1005                              <1> 
  1006                              <1> 	; 10/10/2017
  1007                              <1> 	; 09/10/2017
  1008                              <1> 	;test	byte [audio_flag_eol], VIA_REG_STAT_FLAG
  1009                              <1> 	;jz	short _ih2 ; EOL
  1010                              <1> 
  1011                              <1> 	; 22/07/2020
  1012                              <1> 	; 14/10/2017
  1013                              <1> 	;test	byte [audio_flag_eol], VIA_REG_STAT_EOL
  1014                              <1> 	;jnz	short _ih2 ; EOL
  1015                              <1> 	;		   ; (Half Buffer 2 has been completed 
  1016                              <1> 	;		   ; and Half Buffer 1 will be played.)
  1017                              <1> 	
  1018                              <1> 	; FLAG  
  1019                              <1> 	; (Half Buffer 1 has been completed 
  1020                              <1> 	;  and Half Buffer 2 will be played.)
  1021                              <1> 
  1022                              <1> 	; 14/10/2017
  1023                              <1> 	;; (Continue to play.)
  1024                              <1> 	;mov	al, VIA_REG_CTRL_INT
  1025                              <1>        	;or	al, VIA_REG_CTRL_START
  1026                              <1>        	;mov	dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_CONTROL
  1027                              <1>         ;call	ctrl_io_w8
  1028                              <1> 	; 12/10/2017
  1029                              <1> 	;mov	byte [audio_flag], 1 
  1030                              <1> 
  1031                              <1> 	; 22/07/2020
  1032                              <1> 	;inc	byte [audio_flag] ; = 1
  1033                              <1> _ih2: 
  1034                              <1> 	; 10/10/2017
  1035 00012339 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff]
  1036 0001233F 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size]
  1037 00012345 D1E9                <1> 	shr	ecx, 1 ; dma buff size / 2 = half buffer size
  1038                              <1> 	
  1039                              <1> 	; 22/07/2020
  1040                              <1> 	; 12/10/2017
  1041                              <1> 	;cmp	byte [audio_flag], 0
  1042                              <1> 	;ja	short _ih3 ; Playing Half Buffer 2 (Current: FLAG)
  1043                              <1> 	
  1044                              <1> 	; 27/07/2020
  1045                              <1> 	; 22/07/2020
  1046 00012347 F605[28710100]01    <1> 	test	byte [audio_flag], 1  ; Current flag value
  1047 0001234E 7402                <1> 	jz	short _ih3 ; Half Buffer 1 must be filled
  1048                              <1> 
  1049                              <1> 	; Half Buffer 2 must be filled
  1050 00012350 01CF                <1> 	add	edi, ecx
  1051                              <1> _ih3:
  1052                              <1> 	; Update half buffer 2 while playing half buffer 1
  1053                              <1> 	; Update half buffer 1 while playing half buffer 2
  1054                              <1> 
  1055 00012352 8B35[18710100]      <1> 	mov	esi, [audio_p_buffer] ; phy addr of audio buff
  1056 00012358 C1E902              <1> 	shr	ecx, 2 ; half buff size / 4
  1057 0001235B F3A5                <1> 	rep	movsd
  1058                              <1> 
  1059                              <1> 	; switch flag value ;
  1060 0001235D 8035[28710100]01    <1> 	xor	byte [audio_flag], 1
  1061                              <1> 	; 12/10/2017
  1062                              <1> 	; [audio_flag] = 0 : Playing dma half buffer 2
  1063                              <1> 			   ; Next buffer (to update) is dma half buff 1
  1064                              <1> 	; 	       = 1 : Playing dma half buffer 1
  1065                              <1> 			   ; Next buffer (to update) is dma half buff 2
  1066                              <1> _ih4:	
  1067                              <1> 	; 28/05/2017
  1068                              <1> 	;mov	byte [audio_busy], 0 ; 09/10/2017
  1069                              <1> 	;
  1070                              <1> 	;pop	edi
  1071                              <1> 	;pop	esi
  1072                              <1> 	;pop	ebx ; * must be restored !
  1073                              <1> 	;pop	ecx
  1074                              <1> 	;pop	edx
  1075                              <1> 	;pop	eax ; * must be restored !
  1076                              <1> 
  1077 00012364 C3                  <1> 	retn
  1078                              <1> 
  1079                              <1> channel_reset:
  1080                              <1> 	; 24/06/2017
  1081                              <1> 	; 29/05/2017
  1082                              <1> 	; 23/03/2017
  1083                              <1> 	; 14/11/2016 - Erdogan Tan
  1084                              <1> 	; 12/11/2016 - Erdogan Tan (Ref: KolibriOS, vt823x.asm)
  1085 00012365 BA01000000          <1>         mov	edx, VIA_REG_OFFSET_CONTROL
  1086                              <1>         ;mov	eax, VIA_REG_CTRL_PAUSE + VIA_REG_CTRL_TERMINATE + VIA_REG_CTRL_RESET
  1087 0001236A B848000000          <1>         mov	eax, VIA_REG_CTRL_PAUSE + VIA_REG_CTRL_TERMINATE ; 24/06/2017       
  1088 0001236F E88BFEFFFF          <1> 	call    ctrl_io_w8
  1089                              <1> 
  1090                              <1>         ;mov	edx, VIA_REG_OFFSET_CONTROL
  1091                              <1>         ;call   ctrl_io_r8
  1092                              <1> 
  1093                              <1> 	; wait for 50 ms
  1094 00012374 B9A0000000          <1> 	mov	ecx, 160 ; (200*0.25 ms) ; 29/05/2017	
  1095                              <1> _ch_rst_wait:
  1096 00012379 E849FEFFFF          <1> 	call	delay1_4ms
  1097 0001237E 49                  <1> 	dec	ecx
  1098 0001237F 75F8                <1> 	jnz	short _ch_rst_wait     
  1099                              <1> 
  1100                              <1>         ; disable interrupts
  1101 00012381 BA01000000          <1>         mov	edx, VIA_REG_OFFSET_CONTROL
  1102 00012386 31C0                <1>         xor     eax, eax
  1103 00012388 E872FEFFFF          <1>         call    ctrl_io_w8
  1104                              <1> 
  1105                              <1>         ; clear interrupts
  1106 0001238D BA00000000          <1>         mov	edx, VIA_REG_OFFSET_STATUS
  1107 00012392 B803000000          <1> 	mov	eax, 3
  1108 00012397 E863FEFFFF          <1>         call	ctrl_io_w8
  1109                              <1> 
  1110                              <1> 	;mov	edx, VIA_REG_OFFSET_CURR_PTR
  1111                              <1> 	;xor	eax, eax
  1112                              <1> 	;call	ctrl_io_w32
  1113                              <1> 
  1114 0001239C C3                  <1>         retn	
  1115                              <1> 
  1116                              <1> vt8233_stop: ; 22/04/2017
  1117 0001239D C605[34710100]00    <1> 	mov	byte [audio_play_cmd], 0 ; stop !
  1118                              <1> _tlp2:
  1119                              <1> 	; 24/06/2017
  1120                              <1>         ; finished with song, stop everything
  1121                              <1> 	;mov	al, VIA_REG_CTRL_INT
  1122                              <1>         ;or	al, VIA_REG_CTRL_TERMINATE
  1123                              <1> 	;mov	dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_CONTROL
  1124                              <1>         ;call	ctrl_io_w8
  1125                              <1> 
  1126                              <1>         ;call	channel_reset
  1127                              <1> 	;retn
  1128                              <1> 
  1129 000123A4 EBBF                <1> 	jmp	short channel_reset
  1130                              <1> 
  1131                              <1> set_vt8233_bdl: ; Set VT8237R Buffer Descriptor List
  1132                              <1> 	; 22/07/2020 - TRDOS 386 v2.0.2
  1133                              <1> 	; 28/05/2017
  1134                              <1> 	; 21/04/2017 (TRDOS 386 kernel, 'audio.s')
  1135                              <1> 	; 24/03/2017 - 'PLAYER.COM' ('via_wav.asm' - 29/11/2016) 
  1136                              <1> 	
  1137                              <1> 	; eax = dma buffer address = [audio_DMA_buff]
  1138                              <1> 	; ecx = dma buffer buffer size = [audio_dmabuff_size]
  1139                              <1> 
  1140 000123A6 D1E9                <1> 	shr	ecx, 1 ; dma half buffer size
  1141 000123A8 89CE                <1> 	mov	esi, ecx
  1142                              <1> 
  1143 000123AA BF[3C710100]        <1>         mov     edi, audio_bdl_buff	; get BDL address
  1144 000123AF B910000000          <1>         mov     ecx, 32 / 2		; make 32 entries in BDL
  1145                              <1> 
  1146 000123B4 EB05                <1> 	jmp	short s_vt8233_bdl1 
  1147                              <1> 
  1148                              <1> s_vt8233_bdl0:
  1149                              <1> 	; set buffer descriptor 0 to start of data file in memory
  1150                              <1> 
  1151 000123B6 A1[20710100]        <1>  	mov	eax, [audio_dma_buff]	; Physical address of DMA buffer
  1152                              <1>  
  1153                              <1> s_vt8233_bdl1:
  1154 000123BB AB                  <1> 	stosd				; store dmabuffer1 address
  1155                              <1> 
  1156 000123BC 89C2                <1> 	mov	edx, eax
  1157                              <1> 
  1158                              <1> ; VIA VT8235.PDF: (Page 110) (Erdogan Tan, 29/11/2016)
  1159                              <1> 	;
  1160                              <1> 	; 	Audio SGD Table Format
  1161                              <1> 	;	-------------------------------
  1162                              <1> 	;	63   62    61-56    55-32  31-0
  1163                              <1> 	;	--   --   --------  -----  ----
  1164                              <1> 	;	EOL FLAG -reserved- Base   Base
  1165                              <1> 	;		    	    Count  Address
  1166                              <1> 	;		            [23:0] [31:0]
  1167                              <1> 	;	EOL: End Of Link. 
  1168                              <1> 	;	     1 indicates this block is the last of the link.
  1169                              <1> 	;	     If the channel Interrupt on EOL bit is set, then
  1170                              <1> 	;	     an interrupt is generated at the end of the transfer.
  1171                              <1> 	;
  1172                              <1> 	;	FLAG: Block Flag. If set, transfer pauses at the end of this
  1173                              <1> 	;	      block. If the channel Interrupt on FLAG bit is set,
  1174                              <1> 	;	      then an interrupt is generated at the end of this block.
  1175                              <1> 
  1176 000123BE 89F0                <1> 	mov	eax, esi ; DMA half buffer size
  1177 000123C0 01C2                <1> 	add	edx, eax
  1178 000123C2 0D00000040          <1> 	or	eax, FLAG
  1179                              <1> 	;or	eax, EOL
  1180 000123C7 AB                  <1> 	stosd
  1181                              <1> 
  1182                              <1> ; 2nd buffer:
  1183                              <1> 
  1184 000123C8 89D0                <1>         mov	eax, edx ; Physical address of the 2nd half of DMA buffer	
  1185 000123CA AB                  <1> 	stosd		 ; store dmabuffer2 address
  1186                              <1> 
  1187                              <1> ; set length to [audio_dmabuff_size]/2
  1188                              <1> ; Set control (bits 31:16) to BUP, bits 15:0=number of samples
  1189                              <1> ; 
  1190 000123CB 89F0                <1> 	mov	eax, esi ; DMA half buffer size
  1191                              <1> 	; 22/07/2020
  1192                              <1> 	;or	eax, EOL
  1193 000123CD 0D00000040          <1> 	or	eax, FLAG
  1194 000123D2 AB                  <1> 	stosd
  1195                              <1> 
  1196 000123D3 E2E1                <1> 	loop    s_vt8233_bdl0
  1197                              <1> 
  1198                              <1> 	; 22/07/2020
  1199 000123D5 814FFC00000080      <1> 	or	dword [edi-4], EOL
  1200                              <1> 	
  1201 000123DC C3                  <1> 	retn
  1202                              <1> 
  1203                              <1> vt8233_start_play:
  1204                              <1> 	; 01/09/2020 
  1205                              <1> 	; 22/07/2020 
  1206                              <1> 	; start to play audio data via VT8233 audio controller
  1207                              <1> 	; 13/06/2017
  1208                              <1> 	; 10/06/2017
  1209                              <1> 	; 24/04/2017 
  1210                              <1> 	; 21/04/2017 (TRDOS 386 kernel, 'audio.s')
  1211                              <1> 	; 24/03/2017 - 'PLAYER.COM' ('via_wav.asm' - 29/11/2016) 
  1212                              <1> 	; write buffer descriptor list address
  1213                              <1> 
  1214                              <1> 	; Extended Audio Status (2Ah)
  1215 000123DD B82A000000          <1> 	mov	eax, CODEC_EXT_AUDIO_CTRL_REG ; 2Ah 
  1216 000123E2 E83CFEFFFF          <1> 	call	codec_read
  1217 000123E7 25FDFF0000          <1> 	and     eax, 0FFFFh - 2		; clear DRA (BIT1)
  1218                              <1> 	;or     eax, 1			; set VRA (BIT0)
  1219                              <1> 	;or	eax, 5  	; VRA (BIT0) & S/PDIF (BIT2) ; 14/11/2016
  1220 000123EC 0C05                <1> 	or	al, 5
  1221                              <1> 	; 01/09/2020	
  1222                              <1> 	;or	eax, 3805h ; AD1980 (PRK, PRJ, PRI = 1 .. only front DAC)
  1223                              <1> 	; 01/09/2020
  1224                              <1> 	;mov	edx, CODEC_EXT_AUDIO_CTRL_REG
  1225                              <1> 	;cmp	word [audio_freq], 0BB80h ; 48 kHz
  1226                              <1> 	;jne	short set_extd_audio_status_1
  1227                              <1> 	;and	al, 0FEh ; disable VRA bit (set sample rate to 48000 Hz)
  1228                              <1> 	;jmp	short set_extd_audio_status_2
  1229                              <1> ;set_extd_audio_status_1:
  1230 000123EE BA2A000000          <1> 	mov	edx, CODEC_EXT_AUDIO_CTRL_REG
  1231 000123F3 E857FEFFFF          <1> 	call	codec_write
  1232                              <1> 	;jc	short cconfig_error
  1233                              <1> 
  1234                              <1> set_sample_rate:
  1235                              <1> 	;movzx	eax, word [audio_freq]
  1236 000123F8 66A1[32710100]      <1> 	mov	ax, [audio_freq]
  1237 000123FE BA2C000000          <1> 	mov	edx, CODEC_PCM_FRONT_DACRATE_REG ; 2Ch ; PCM Front DAC Rate
  1238                              <1> ;set_extd_audio_status_2:
  1239 00012403 E847FEFFFF          <1> 	call	codec_write
  1240                              <1> 
  1241                              <1> 	; 01/09/2020
  1242                              <1> 	; set AD1980 MCB register (Index 76h) to 0C00h
  1243                              <1> 	; (CLDIS, HPSEL)
  1244                              <1> 	;mov	ax, 0C00h
  1245                              <1> 	;mov	edx, CODEC_MISC_CRTL_BITS_REG ; 76h 
  1246                              <1> 	;			; Miscellaneous Control Bit Register
  1247                              <1> 	;call	codec_write
  1248                              <1> 	;
  1249                              <1> 
  1250 00012408 B8[3C710100]        <1>         mov	eax, audio_bdl_buff
  1251                              <1>   
  1252                              <1> 	; 12/11/2016 - Erdogan Tan 
  1253                              <1> 	; (Ref: KolibriOS, vt823x.asm, 'create_primary_buff')
  1254 0001240D BA04000000          <1> 	mov	edx, VIADEV_PLAYBACK + VIA_REG_OFFSET_TABLE_PTR
  1255 00012412 E8FAFDFFFF          <1>         call	ctrl_io_w32
  1256                              <1> 
  1257                              <1> 	;call	codec_check_ready
  1258                              <1> 
  1259 00012417 66BA0200            <1>   	mov	dx, VIADEV_PLAYBACK + VIA_REG_OFS_PLAYBACK_VOLUME_L
  1260                              <1>         ;mov	eax, 2	; 31
  1261 0001241B B01F                <1> 	mov	al, 31
  1262 0001241D 2A05[36710100]      <1>         sub	al, [audio_master_volume_l]
  1263 00012423 E8D7FDFFFF          <1> 	call	ctrl_io_w8
  1264                              <1> 
  1265                              <1> 	;call	codec_check_ready
  1266                              <1> 
  1267 00012428 66BA0300            <1>         mov     dx, VIADEV_PLAYBACK + VIA_REG_OFS_PLAYBACK_VOLUME_R
  1268                              <1>         ;mov	ax, 2	; 31
  1269 0001242C B01F                <1> 	mov	al, 31
  1270 0001242E 2A05[37710100]      <1>         sub	al, [audio_master_volume_r]
  1271 00012434 E8C6FDFFFF          <1> 	call    ctrl_io_w8
  1272                              <1> 
  1273                              <1> 	;call	codec_check_ready
  1274                              <1> ;
  1275                              <1> ;
  1276                              <1> ; All set. Let's play some music.
  1277                              <1> ;
  1278                              <1> ;
  1279                              <1>        	;mov    dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_STOP_IDX
  1280                              <1>         ;mov    ax, VIA8233_REG_TYPE_16BIT or VIA8233_REG_TYPE_STEREO or 0xfffff or 0xff000000
  1281                              <1>         ;call   ctrl_io_w32
  1282                              <1> 
  1283                              <1> 	;call	codec_check_ready
  1284                              <1> 
  1285                              <1> 	; 08/12/2016
  1286                              <1> 	; 07/10/2016
  1287                              <1>         ;;mov    al, 1
  1288                              <1>         ;mov	al, 31
  1289                              <1> 	; 22/07/2020
  1290 00012439 B0FF                <1> 	mov	al, 0FFh
  1291 0001243B E813000000          <1> 	call    set_VT8233_LastValidIndex
  1292                              <1> 
  1293 00012440 C605[34710100]01    <1> 	mov	byte [audio_play_cmd], 1 ; play command (do not stop) !
  1294                              <1> 
  1295                              <1> 	; 22/07/2020
  1296                              <1> 	;mov	byte [audio_flag], 0  ; clear half buffer flag
  1297                              <1> 
  1298                              <1> vt8233_play: ; continue to play
  1299                              <1> 	; 22/04/2017
  1300                              <1> 	;mov	al, VIA_REG_CTRL_INT
  1301                              <1>        	;or	al, VIA_REG_CTRL_START
  1302                              <1>         ;;mov	al, VIA_REG_CTRL_AUTOSTART + VIA_REG_CTRL_START
  1303                              <1> 	; 22/07/2020	
  1304 00012447 B0A1                <1> 	mov	al, VIA_REG_CTRL_AUTOSTART + VIA_REG_CTRL_START + VIA_REG_CTRL_INT_FLAG
  1305                              <1> 
  1306 00012449 66BA0100            <1> 	mov     dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_CONTROL
  1307 0001244D E8ADFDFFFF          <1>         call    ctrl_io_w8
  1308                              <1> 	;call	codec_check_ready
  1309                              <1> 	;retn
  1310                              <1> 	;jmp	codec_check_ready
  1311 00012452 C3                  <1> 	retn
  1312                              <1> 
  1313                              <1> ;input AL = index # to stop on
  1314                              <1> set_VT8233_LastValidIndex:
  1315                              <1> 	; 23/07/2020
  1316                              <1> 	; 10/06/2017
  1317                              <1> 	; 21/04/2017 (TRDOS 386 kernel, 'audio.s')
  1318                              <1> 	; 24/03/2017 - 'PLAYER.COM' ('via_wav.asm' - 29/11/2016) 
  1319                              <1> 	; 19/11/2016
  1320                              <1> 	; 14/11/2016 - Erdogan Tan (Ref: VIA VT8235.PDF, Page 110)
  1321                              <1> 	; 12/11/2016 - Erdogan Tan
  1322                              <1> 	; (Ref: KolibriOS, vt823x.asm, 'create_primary_buff')
  1323                              <1> 	;push	edx
  1324                              <1> 	;push	ax
  1325 00012453 50                  <1> 	push	eax ; 23/07/2020
  1326                              <1> 	;push	ecx
  1327 00012454 0FB705[32710100]    <1> 	movzx	eax, word [audio_freq] ; Hertz
  1328 0001245B BA00001000          <1> 	mov	edx, 100000h ; 2^20 = 1048576
  1329 00012460 F7E2                <1> 	mul	edx
  1330 00012462 B980BB0000          <1> 	mov	ecx, 48000	
  1331 00012467 F7F1                <1> 	div	ecx
  1332                              <1> 	;and	eax, 0FFFFFh
  1333                              <1> 	;pop	ecx
  1334                              <1> 	;pop	dx 
  1335 00012469 5A                  <1> 	pop	edx ; 23/07/2020
  1336 0001246A C1E218              <1> 	shl	edx, 24  ; STOP Index Setting: Bit 24 to 31
  1337 0001246D 09D0                <1> 	or	eax, edx
  1338                              <1> 	; 19/11/2016
  1339 0001246F 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16
  1340 00012476 7505                <1> 	jne	short sLVI_1
  1341 00012478 0D00002000          <1> 	or	eax, VIA8233_REG_TYPE_16BIT
  1342                              <1> sLVI_1:
  1343 0001247D 803D[31710100]02    <1> 	cmp	byte [audio_stmo], 2
  1344 00012484 7505                <1> 	jne	short sLVI_2
  1345 00012486 0D00001000          <1> 	or	eax, VIA8233_REG_TYPE_STEREO
  1346                              <1> sLVI_2:
  1347 0001248B BA08000000          <1> 	mov     edx, VIADEV_PLAYBACK + VIA_REG_OFFSET_STOP_IDX
  1348 00012490 E87CFDFFFF          <1>         call    ctrl_io_w32
  1349                              <1> 	;call	codec_check_ready
  1350                              <1> 	;pop	edx
  1351 00012495 C3                  <1> 	retn
  1352                              <1> 
  1353                              <1> vt8233_pause: ; pause
  1354                              <1> 	; 10/06/2017
  1355                              <1> 	; 22/04/2017
  1356                              <1> 	;mov     al, VIA_REG_CTRL_INT
  1357                              <1>         ;or      al, VIA_REG_CTRL_PAUSE
  1358                              <1> 	; 23/07/2020
  1359 00012496 B029                <1> 	mov	al, VIA_REG_CTRL_PAUSE+VIA_REG_CTRL_INT_FLAG+VIA_REG_CTRL_AUTOSTART
  1360                              <1> 	
  1361 00012498 66BA0100            <1> 	mov     dx, VIADEV_PLAYBACK + VIA_REG_OFFSET_CONTROL
  1362 0001249C E85EFDFFFF          <1>         call    ctrl_io_w8
  1363                              <1> 	;call	codec_check_ready
  1364                              <1> 	;retn
  1365                              <1> 	;jmp	codec_check_ready
  1366 000124A1 C3                  <1> 	retn
  1367                              <1> 
  1368                              <1> vt8233_reset: 
  1369                              <1> 	; 22/04/2017
  1370                              <1> 	; reset VT8237R (vt8233) Audio Controller
  1371                              <1> 	;cmp	byte [audio_play_cmd], 1
  1372                              <1> 	;jna	short vt8233_rst_0
  1373 000124A2 C605[34710100]00    <1> 	mov	byte [audio_play_cmd], 0 ; stop !
  1374                              <1> vt8233_rst_0:
  1375 000124A9 E8B0FCFFFF          <1> 	call	reset_codec
  1376 000124AE 720A                <1> 	jc	short vt8233_rst_1 ; codec error !
  1377                              <1> 	; eax = 1
  1378 000124B0 E82EFDFFFF          <1> 	call	codec_io_w16 ; w32
  1379 000124B5 E8ABFEFFFF          <1> 	call	channel_reset
  1380                              <1> vt8233_rst_1:
  1381 000124BA C3                  <1> 	retn
  1382                              <1> 
  1383                              <1> vt8233_volume:
  1384                              <1> 	; set VT8237R (vt8233) sound volume level
  1385                              <1> 	; 24/04/2017
  1386                              <1> 	; 22/04/2017
  1387                              <1> 	; bl = component (0 = master/playback/lineout volume)
  1388                              <1> 	; cl = left channel volume level (0 to 31)
  1389                              <1> 	; ch = right channel volume level (0 to 31)
  1390                              <1> 
  1391 000124BB 08DB                <1> 	or	bl, bl
  1392 000124BD 7520                <1> 	jnz	short vt8233_vol_1 ; temporary !
  1393 000124BF 66B81F1F            <1> 	mov	ax, 1F1Fh ; 31,31
  1394 000124C3 38C1                <1> 	cmp	cl, al
  1395 000124C5 7718                <1> 	ja	short vt8233_vol_1 ; temporary !
  1396 000124C7 38E5                <1> 	cmp	ch, ah
  1397 000124C9 7714                <1> 	ja	short vt8233_vol_1 ; temporary !
  1398 000124CB 66890D[36710100]    <1> 	mov	[audio_master_volume], cx
  1399 000124D2 6629C8              <1> 	sub	ax, cx
  1400 000124D5 BA02000000          <1> 	mov	edx, CODEC_MASTER_VOL_REG ; 02h ; Line Out
  1401 000124DA E870FDFFFF          <1> 	call	codec_write
  1402                              <1> vt8233_vol_1:
  1403 000124DF C3                  <1> 	retn
  1404                              <1> 
  1405                              <1> ; CODE for SOUND BLASTER 16
  1406                              <1> 
  1407                              <1> DetectSB:
  1408                              <1> 	; 24/04/2017
  1409                              <1> 	;pushad
  1410                              <1> ScanPort:
  1411 000124E0 66BB1002            <1> 	mov     bx, 210h	; start scanning ports
  1412                              <1> 				; 210h, 220h, .. 260h
  1413                              <1> ResetDSP:       
  1414 000124E4 6689DA              <1> 	mov     dx, bx		; try to reset the DSP.
  1415 000124E7 6683C206            <1> 	add     dx, 06h
  1416 000124EB B001                <1> 	mov	al, 1
  1417 000124ED EE                  <1> 	out	dx, al
  1418                              <1> 
  1419 000124EE EC                  <1> 	in	al, dx
  1420 000124EF EC                  <1> 	in	al, dx
  1421 000124F0 EC                  <1> 	in	al, dx
  1422 000124F1 EC                  <1> 	in	al, dx
  1423                              <1> 
  1424 000124F2 30C0                <1> 	xor     al, al
  1425 000124F4 EE                  <1> 	out	dx, al
  1426                              <1> 
  1427 000124F5 6683C208            <1> 	add     dx, 08h
  1428 000124F9 66B96400            <1> 	mov	cx, 100
  1429                              <1> WaitID:
  1430 000124FD EC                  <1> 	in	al, dx
  1431 000124FE 08C0                <1> 	or      al, al
  1432 00012500 7804                <1> 	js      short GetID
  1433 00012502 E2F9                <1> 	loop    WaitID
  1434 00012504 EB0F                <1> 	jmp     short NextPort
  1435                              <1> GetID:          
  1436 00012506 6683EA04            <1> 	sub     dx, 04h
  1437 0001250A EC                  <1> 	in	al, dx
  1438 0001250B 3CAA                <1> 	cmp     al, 0AAh
  1439 0001250D 7413                <1> 	je      short Found
  1440 0001250F 6683C204            <1> 	add     dx, 04h
  1441 00012513 E2E8                <1> 	loop    WaitID
  1442                              <1> NextPort:
  1443 00012515 6683C310            <1> 	add     bx, 10h		; if not response,
  1444 00012519 6681FB6002          <1> 	cmp     bx, 260h	; try the next port.
  1445 0001251E 76C4                <1> 	jbe     short ResetDSP
  1446 00012520 F9                  <1> 	stc
  1447 00012521 C3                  <1> 	retn
  1448                              <1> Found:
  1449 00012522 66891D[06710100]    <1> 	mov     [audio_io_base], bx	; SB Port Address Found!
  1450                              <1> ScanIRQ:
  1451                              <1> SetIrqs:
  1452 00012529 28C0                <1> 	sub 	al, al ; 0
  1453 0001252B A2[FE700100]        <1> 	mov 	[IRQnum], al ; reset
  1454 00012530 A2[03710100]        <1> 	mov	[audio_intr], al ; reset
  1455                              <1> 
  1456                              <1> 	; ah > 0 -> set IRQ vector
  1457                              <1> 	; al = IRQ number
  1458                              <1> 	;mov	ax, 103h ; IRQ 3
  1459                              <1> 	;call	set_hardware_int_vector
  1460                              <1> 	;mov	ax, 104h ; IRQ 4
  1461                              <1> 	;call	set_hardware_int_vector
  1462 00012535 66B80501            <1> 	mov	ax, 105h ; IRQ 5
  1463 00012539 E8EFDDFFFF          <1> 	call	set_hardware_int_vector
  1464 0001253E 66B80701            <1> 	mov	ax, 107h ; IRQ 7
  1465 00012542 E8E6DDFFFF          <1> 	call	set_hardware_int_vector
  1466                              <1> 
  1467 00012547 668B15[06710100]    <1> 	mov     dx, [audio_io_base] ; tells to the SB to
  1468 0001254E 6683C20C            <1> 	add     dx, 0Ch		    ; generate a IRQ!
  1469                              <1> WaitSb:
  1470 00012552 EC                  <1> 	in	al, dx
  1471 00012553 08C0                <1> 	or      al, al
  1472 00012555 78FB                <1> 	js      short WaitSb
  1473 00012557 B0F2                <1> 	mov     al, 0F2h
  1474 00012559 EE                  <1> 	out	dx, al
  1475                              <1> 
  1476 0001255A 31C9                <1> 	xor     ecx, ecx	; wait until IRQ level
  1477                              <1> WaitIRQ: 
  1478 0001255C A0[FE700100]        <1> 	mov	al, [IRQnum]
  1479 00012561 3C00                <1> 	cmp     al, 0 ; is changed or timeout.
  1480 00012563 7706                <1> 	ja	short IrqOk
  1481 00012565 6649                <1> 	dec	cx
  1482 00012567 75F3                <1> 	jnz	short WaitIRQ
  1483 00012569 EB15                <1> 	jmp	short RestoreIrqs
  1484                              <1> IrqOk:
  1485 0001256B A2[03710100]        <1> 	mov	[audio_intr], al ; set   
  1486 00012570 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1487 00012577 6683C20E            <1> 	add     dx, 0Eh
  1488 0001257B EC                  <1> 	in	al, dx	; SB acknowledge.
  1489 0001257C B020                <1> 	mov	al, 20h
  1490 0001257E E620                <1> 	out	20h, al	; Hardware acknowledge.
  1491                              <1> 
  1492                              <1> RestoreIrqs:
  1493                              <1> 	; ah = 0 -> reset IRQ vector
  1494                              <1> 	; al = IRQ number
  1495                              <1> 	;mov	ax, 3 ; IRQ 3
  1496                              <1> 	;call	set_hardware_int_vector
  1497                              <1> 	;mov	ax, 4 ; IRQ 4
  1498                              <1> 	;call	set_hardware_int_vector
  1499 00012580 66B80500            <1> 	mov	ax, 5 ; IRQ 5
  1500 00012584 E8A4DDFFFF          <1> 	call	set_hardware_int_vector
  1501 00012589 66B80700            <1> 	mov	ax, 7 ; IRQ 7
  1502 0001258D E89BDDFFFF          <1> 	call	set_hardware_int_vector
  1503                              <1> 
  1504 00012592 31D2                <1> 	xor	edx, edx
  1505 00012594 8915[08710100]      <1> 	mov	[audio_dev_id], edx ; 0
  1506 0001259A 8915[0C710100]      <1> 	mov	[audio_vendor], edx ; 0
  1507 000125A0 8915[10710100]      <1> 	mov	[audio_stats_cmd], edx ; 0
  1508                              <1> 
  1509                              <1> 	;popad
  1510                              <1> 
  1511 000125A6 803D[03710100]01    <1> 	cmp     byte [audio_intr], 1 ; IRQ level was changed?
  1512                              <1> 	
  1513 000125AD C3                  <1> 	retn
  1514                              <1> 
  1515                              <1> %macro	SbOut	1
  1516                              <1> %%Wait:
  1517                              <1> 	in	al, dx
  1518                              <1> 	or	al, al
  1519                              <1> 	js	short %%Wait
  1520                              <1> 	mov	al, %1
  1521                              <1> 	out	dx, al
  1522                              <1> %endmacro
  1523                              <1> 
  1524                              <1> SbInit_play:
  1525                              <1> 	; 22/10/2017
  1526                              <1> 	; 20/10/2017
  1527                              <1> 	; 06/10/2017
  1528                              <1> 	; 13/07/2017, 09/08/2017
  1529                              <1> 	; 24/04/2017, 15/05/2017, 24/06/2017
  1530                              <1> 	;pushad
  1531                              <1> SetBuffer:
  1532                              <1> 	;mov	byte [DmaFlag], 0
  1533                              <1> 
  1534 000125AE 8B1D[20710100]      <1> 	mov	ebx, [audio_dma_buff] ; physical addr of DMA buff
  1535 000125B4 89DF                <1> 	mov	edi, ebx
  1536 000125B6 8B0D[24710100]      <1> 	mov     ecx, [audio_dmabuff_size]
  1537                              <1> 
  1538 000125BC 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16
  1539 000125C3 7531                <1> 	jne	short sbInit_0 ; set 8 bit DMA buffer
  1540                              <1> 	
  1541                              <1> 	; 09/08/2017
  1542                              <1> 	; convert byte count to word count
  1543 000125C5 D1E9                <1> 	shr	ecx, 1
  1544 000125C7 49                  <1> 	dec	ecx ; word count - 1
  1545                              <1> 	; convert byte offset to word offset
  1546 000125C8 D1EB                <1> 	shr	ebx, 1
  1547                              <1> 
  1548                              <1> 	; 16 bit DMA buffer setting (DMA channel 5)
  1549 000125CA B005                <1> 	mov     al, 05h  ; set mask bit for channel 5  (4+1)
  1550 000125CC E6D4                <1> 	out	0D4h, al
  1551                              <1> 	
  1552 000125CE 30C0                <1> 	xor     al, al   ; stops all DMA processes on selected channel
  1553 000125D0 E6D8                <1> 	out	0D8h, al ; clear selected channel register
  1554                              <1> 
  1555 000125D2 88D8                <1> 	mov     al, bl	 ; byte 0 of DMA buffer offset in words (physical) 
  1556 000125D4 E6C4                <1> 	out	0C4h, al ; DMA channel 5 port number
  1557                              <1> 
  1558 000125D6 88F8                <1> 	mov     al, bh   ; byte 1 of DMA buffer offset in words (physical)   
  1559 000125D8 E6C4                <1> 	out	0C4h, al
  1560                              <1> 	
  1561                              <1> 	; 09/08/2017
  1562 000125DA C1EB0F              <1> 	shr	ebx, 15	 ; complete 16 bit shift
  1563 000125DD 80E3FE              <1> 	and	bl, 0FEh ; clear bit 0 (not necessary, it will be ignored)
  1564                              <1> 
  1565 000125E0 88D8                <1> 	mov     al, bl   ; byte 2 of DMA buffer address (physical) 
  1566 000125E2 E68B                <1> 	out	8Bh, al  ; page register port addr for channel 5 ; 13/07/2017
  1567                              <1> 
  1568 000125E4 88C8                <1> 	mov     al, cl   ; low byte of DMA count - 1
  1569 000125E6 E6C6                <1> 	out	0C6h, al ; count register port addr for channel 1
  1570                              <1> 
  1571 000125E8 88E8                <1> 	mov     al, ch   ; high byte of DMA count - 1
  1572 000125EA E6C6                <1> 	out	0C6h, al
  1573                              <1> 
  1574                              <1> 	; channel 5, read, autoinitialized, single mode
  1575                              <1> 	;mov	al, 49h
  1576 000125EC B059                <1> 	mov	al, 59h  ; 06/10/2017 
  1577 000125EE E6D6                <1> 	out	0D6h, al ; DMA mode register port address
  1578                              <1> 
  1579 000125F0 B001                <1> 	mov     al, 01h  ; clear mask bit for channel 1
  1580 000125F2 E6D4                <1> 	out	0D4h, al ; DMA mask register port address
  1581                              <1> 
  1582 000125F4 EB28                <1> 	jmp	short ClearBuffer
  1583                              <1> 
  1584                              <1> sbInit_0:    
  1585 000125F6 49                  <1> 	dec     ecx ; 09/08/2017
  1586                              <1> 
  1587                              <1> 	; 8 bit DMA buffer setting (DMA channel 1)
  1588 000125F7 B005                <1> 	mov     al, 05h ; set mask bit for channel 1  (4+1)
  1589 000125F9 E60A                <1> 	out	0Ah, al ; DMA mask register
  1590                              <1> 
  1591 000125FB 30C0                <1> 	xor     al, al  ; stops all DMA processes on selected channel
  1592 000125FD E60C                <1> 	out	0Ch, al ; clear selected channel register
  1593                              <1> 
  1594 000125FF 88D8                <1> 	mov     al, bl	; byte 0 of DMA buffer address (physical)   
  1595 00012601 E602                <1> 	out	02h, al ; DMA channel 1 port number
  1596                              <1> 
  1597 00012603 88F8                <1> 	mov     al, bh  ; byte 1 of DMA buffer address (physical)   
  1598 00012605 E602                <1> 	out	02h, al
  1599                              <1> 
  1600 00012607 C1EB10              <1> 	shr	ebx, 16
  1601                              <1> 
  1602 0001260A 88D8                <1> 	mov     al, bl  ; byte 2 of DMA buffer address (physical)   
  1603 0001260C E683                <1> 	out	83h, al ; page register port addr for channel 1
  1604                              <1> 
  1605 0001260E 88C8                <1> 	mov     al, cl  ; low byte of DMA count - 1
  1606 00012610 E603                <1> 	out	03h, al ; count register port addr for channel 1
  1607                              <1> 
  1608 00012612 88E8                <1> 	mov     al, ch  ; high byte of DMA count - 1
  1609 00012614 E603                <1> 	out	03h, al
  1610                              <1> 
  1611                              <1> 	; channel 1, read, autoinitialized, single mode
  1612                              <1> 	;mov	al, 49h
  1613 00012616 B059                <1> 	mov	al, 59h ; 06/10/2017 
  1614 00012618 E60B                <1> 	out	0Bh, al ; DMA mode register port address
  1615                              <1> 
  1616 0001261A B001                <1> 	mov     al, 01h ; clear mask bit for channel 1
  1617 0001261C E60A                <1> 	out	0Ah, al ; DMA mask register port address
  1618                              <1> 
  1619                              <1> ClearBuffer:
  1620                              <1> 	;;mov	edi, [audio_dma_buff]
  1621                              <1> 	;;mov	ecx, [audio_dmabuff_size]
  1622                              <1> 	;inc	ecx
  1623                              <1> 	;mov     al, 80h
  1624                              <1> 	;;cld
  1625                              <1> 	;rep     stosb
  1626                              <1> SetIrq:
  1627                              <1> 	;mov	ebx, SbIrqhandler
  1628                              <1> 	;mov	al, [audio_intr] ; IRQ number	
  1629                              <1> 	;call	set_dev_IRQ_service
  1630                              <1> 	;; SETUP (audio) INTERRUPT CALLBACK SERVICE
  1631                              <1> 	;mov	bl, [audio_intr] ; IRQ number
  1632                              <1> 	;mov	bh, [audio_cb_mode]
  1633                              <1> 	;inc	bh  ; 1 = Signal Response Byte method (fixed value)
  1634                              <1> 	;	    ; 2 = Callback service method
  1635                              <1> 	;	    ; 3 = Auto Increment S.R.B. method 	
  1636                              <1> 	;mov	cl, [audio_srb]
  1637                              <1> 	;mov	edx, [audio_cb_addr]
  1638                              <1> 	;mov	al, [audio_user]
  1639                              <1>  	;call	set_irq_callback_service
  1640                              <1> ResetDsp:
  1641 0001261E 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1642 00012625 6683C206            <1> 	add     dx, 06h
  1643 00012629 B001                <1> 	mov     al, 1
  1644 0001262B EE                  <1> 	out	dx, al
  1645                              <1> 
  1646 0001262C EC                  <1> 	in	al, dx
  1647 0001262D EC                  <1> 	in	al, dx
  1648 0001262E EC                  <1> 	in	al, dx
  1649 0001262F EC                  <1> 	in	al, dx
  1650                              <1> 
  1651 00012630 30C0                <1> 	xor     al, al
  1652 00012632 EE                  <1> 	out	dx, al
  1653                              <1> 
  1654 00012633 66B96400            <1> 	mov     cx, 100
  1655 00012637 28E4                <1> 	sub	ah, ah ; 0
  1656                              <1> WaitId:         
  1657 00012639 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1658 00012640 6683C20E            <1> 	add     dx, 0Eh
  1659 00012644 EC                  <1> 	in	al, dx
  1660 00012645 08C0                <1> 	or      al, al
  1661 00012647 7807                <1> 	js      short sb_GetId
  1662 00012649 E2EE                <1> 	loop    WaitId
  1663 0001264B E9B4000000          <1> 	jmp     sb_Exit
  1664                              <1> sb_GetId:
  1665 00012650 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1666 00012657 6683C20A            <1> 	add     dx, 0Ah
  1667 0001265B EC                  <1> 	in	al, dx
  1668 0001265C 3CAA                <1> 	cmp     al, 0AAh
  1669 0001265E 7407                <1> 	je      short SbOk
  1670 00012660 E2D7                <1> 	loop    WaitId
  1671 00012662 E99D000000          <1> 	jmp	sb_Exit
  1672                              <1> SbOk:
  1673 00012667 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1674 0001266E 6683C20C            <1> 	add     dx, 0Ch
  1675                              <1> 	SbOut   0D1h ; Turn on speaker
  1675                              <2> %%Wait:
  1675 00012672 EC                  <2>  in al, dx
  1675 00012673 08C0                <2>  or al, al
  1675 00012675 78FB                <2>  js short %%Wait
  1675 00012677 B0D1                <2>  mov al, %1
  1675 00012679 EE                  <2>  out dx, al
  1676                              <1> 	SbOut   41h ; 8 bit or 16 bit transfer
  1676                              <2> %%Wait:
  1676 0001267A EC                  <2>  in al, dx
  1676 0001267B 08C0                <2>  or al, al
  1676 0001267D 78FB                <2>  js short %%Wait
  1676 0001267F B041                <2>  mov al, %1
  1676 00012681 EE                  <2>  out dx, al
  1677 00012682 668B1D[32710100]    <1> 	mov	bx, [audio_freq] ; sampling rate (Hz)
  1678                              <1> 	SbOut	bh ; sampling rate high byte
  1678                              <2> %%Wait:
  1678 00012689 EC                  <2>  in al, dx
  1678 0001268A 08C0                <2>  or al, al
  1678 0001268C 78FB                <2>  js short %%Wait
  1678 0001268E 88F8                <2>  mov al, %1
  1678 00012690 EE                  <2>  out dx, al
  1679                              <1> 	SbOut	bl ; sampling rate low byte
  1679                              <2> %%Wait:
  1679 00012691 EC                  <2>  in al, dx
  1679 00012692 08C0                <2>  or al, al
  1679 00012694 78FB                <2>  js short %%Wait
  1679 00012696 88D8                <2>  mov al, %1
  1679 00012698 EE                  <2>  out dx, al
  1680                              <1> 
  1681                              <1> 	; 22/05/2017
  1682 00012699 E8C0000000          <1> 	call	sb16_volume_initial ; 15/05/2017
  1683                              <1> 	; 20/05/2017
  1684                              <1> 	;call	sb16_volume
  1685                              <1> 
  1686                              <1> StartDma:  
  1687                              <1> 	; autoinitialized mode
  1688 0001269E 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit samples
  1689 000126A5 7411                <1> 	je	short sb_play_1
  1690                              <1> 	; 8 bit samples
  1691 000126A7 66BBC600            <1> 	mov	bx, 0C6h ; 8 bit output (0C6h)
  1692 000126AB 803D[31710100]02    <1> 	cmp	byte [audio_stmo], 2 ; 1 = mono, 2 = stereo
  1693 000126B2 7214                <1> 	jb	short sb_play_2
  1694 000126B4 B720                <1> 	mov	bh, 20h	; 8 bit stereo (20h)
  1695 000126B6 EB10                <1> 	jmp	short sb_play_2
  1696                              <1> sb_play_1:
  1697                              <1> 	; 16 bit samples
  1698 000126B8 66BBB610            <1> 	mov	bx, 10B6h ; 16 bit output (0B6h)
  1699 000126BC 803D[31710100]02    <1> 	cmp	byte [audio_stmo], 2 ; 1 = mono, 2 = stereo
  1700 000126C3 7203                <1> 	jb	short sb_play_2
  1701 000126C5 80C720              <1> 	add	bh, 20h	; 16 bit stereo (30h)
  1702                              <1> sb_play_2:     
  1703                              <1> 	; PCM output (8/16 bit mono autoinitialized transfer)
  1704                              <1> 	SbOut   bl ; bCommand
  1704                              <2> %%Wait:
  1704 000126C8 EC                  <2>  in al, dx
  1704 000126C9 08C0                <2>  or al, al
  1704 000126CB 78FB                <2>  js short %%Wait
  1704 000126CD 88D8                <2>  mov al, %1
  1704 000126CF EE                  <2>  out dx, al
  1705                              <1> 	SbOut	bh ; bMode
  1705                              <2> %%Wait:
  1705 000126D0 EC                  <2>  in al, dx
  1705 000126D1 08C0                <2>  or al, al
  1705 000126D3 78FB                <2>  js short %%Wait
  1705 000126D5 88F8                <2>  mov al, %1
  1705 000126D7 EE                  <2>  out dx, al
  1706 000126D8 8B1D[24710100]      <1> 	mov	ebx, [audio_dmabuff_size]  ; 15/05/2017
  1707 000126DE D1EB                <1> 	shr	ebx, 1 ; half buffer size
  1708                              <1> 	; 20/10/2017	
  1709 000126E0 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit DMA
  1710 000126E7 7502                <1> 	jne	short sb_play_3
  1711 000126E9 D1EB                <1> 	shr	ebx, 1 ; byte count to word count
  1712                              <1> sb_play_3: 
  1713 000126EB 664B                <1> 	dec	bx  ; wBlkSize is one less than the actual size 
  1714                              <1> 	SbOut   bl
  1714                              <2> %%Wait:
  1714 000126ED EC                  <2>  in al, dx
  1714 000126EE 08C0                <2>  or al, al
  1714 000126F0 78FB                <2>  js short %%Wait
  1714 000126F2 88D8                <2>  mov al, %1
  1714 000126F4 EE                  <2>  out dx, al
  1715                              <1> 	SbOut   bh
  1715                              <2> %%Wait:
  1715 000126F5 EC                  <2>  in al, dx
  1715 000126F6 08C0                <2>  or al, al
  1715 000126F8 78FB                <2>  js short %%Wait
  1715 000126FA 88F8                <2>  mov al, %1
  1715 000126FC EE                  <2>  out dx, al
  1716                              <1> 
  1717 000126FD C605[34710100]01    <1> 	mov	byte [audio_play_cmd], 1 ; playing !
  1718                              <1> 
  1719                              <1> 	;; Set Voice and master volumes
  1720                              <1> 	;mov	dx, [audio_io_base]
  1721                              <1> 	;add	dl, 4 ; Mixer chip Register Address Port
  1722                              <1> 	;SbOut	30h   ; select Master Volume Register (L)
  1723                              <1> 	;inc	dl    ; Mixer chip Register Data Port
  1724                              <1> 	;SbOut	0F8h  ; Max. volume value is 31 (31*8)
  1725                              <1> 	;dec	dl
  1726                              <1> 	;SbOut	31h   ; select Master Volume Register (R)
  1727                              <1> 	;inc	dl
  1728                              <1> 	;SbOut	0F8h  ; Max. volume value is 31 (31*8)
  1729                              <1> 	;dec	dl
  1730                              <1> 	;SbOut	32h   ; select Voice Volume Register (L)
  1731                              <1> 	;inc	dl
  1732                              <1> 	;SbOut	0F8h  ; Max. volume value is 31 (31*8)
  1733                              <1> 	;dec	dl
  1734                              <1> 	;SbOut	33h   ; select Voice Volume Register (R)
  1735                              <1> 	;inc	dl
  1736                              <1> 	;SbOut	0F8h  ; Max. volume value is 31 (31*8)	
  1737                              <1> 	;;
  1738                              <1> 	;dec	dl
  1739                              <1> 	;SbOut	44h   ; select Treble Register (L)
  1740                              <1> 	;inc	dl
  1741                              <1> 	;SbOut	0F0h  ; Max. Treble value is 15 (15*16)
  1742                              <1> 	;dec	dl
  1743                              <1> 	;SbOut	45h   ; select Treble Register (R)
  1744                              <1> 	;inc	dl
  1745                              <1> 	;SbOut	0F0h  ; Max. Treble value is 15 (15*16)
  1746                              <1> 	;dec	dl
  1747                              <1> 	;SbOut	46h   ; select Bass Register (L)
  1748                              <1> 	;inc	dl
  1749                              <1> 	;SbOut	0F0h  ; Max. Bass value is 15 (15*16)
  1750                              <1> 	;dec	dl
  1751                              <1> 	;SbOut	47h   ; select Bass Register (R)
  1752                              <1> 	;inc	dl
  1753                              <1> 	;SbOut	0F0h  ; Max. Bass value is 15 (15*16)	
  1754                              <1> 
  1755                              <1> sb_Exit:           
  1756                              <1> 	;popad
  1757 00012704 C3                  <1> 	retn
  1758                              <1> 
  1759                              <1> sb16_int_handler:
  1760                              <1> 	; Interrupt Handler for Sound Blaster 16 Audio Card
  1761                              <1> 	; Note: called by 'dev_IRQ_service'
  1762                              <1> 	; 20/10/2017
  1763                              <1> 	; 12/10/2017
  1764                              <1> 	; 10/10/2017 
  1765                              <1> 	; 12/05/2017, 09/10/2017
  1766                              <1> 	; 24/04/2017 (TRDOS 386 kernel, 'audio.s')
  1767                              <1> 	; 10/03/2017 - 'PLAYWAV.PRG' ('playwav.s') 
  1768                              <1> 
  1769                              <1> 	;push	eax ; * must be saved !
  1770                              <1> 	;push	ebx ; * must be saved !
  1771                              <1> 	;push	ecx
  1772                              <1> 	;push	edx
  1773                              <1> 	;push	esi
  1774                              <1> 	;push	edi
  1775                              <1> 
  1776 00012705 668B15[06710100]    <1> 	mov     dx, [audio_io_base]
  1777                              <1> 	; 20/10/2017
  1778 0001270C 80C20F              <1> 	add     dl, 0Fh ; 2xFh (DSP 16 bit intr ack)
  1779 0001270F 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16
  1780 00012716 7402                <1> 	je	short sb_irq_16bit_ack
  1781                              <1> sb_irq_8bit_ack:
  1782 00012718 FECA                <1> 	dec	dl  ; 2xEh (DSP 8 bit intr ack)
  1783                              <1> sb_irq_16bit_ack:
  1784 0001271A EC                  <1> 	in	al, dx
  1785                              <1> 
  1786                              <1> 	;cmp	byte [audio_busy], 0
  1787                              <1> 	;ja	short sb_irq_h3
  1788                              <1> 
  1789                              <1> 	;mov	byte [audio_busy], 1
  1790                              <1> 
  1791 0001271B 803D[34710100]01    <1> 	cmp	byte [audio_play_cmd], 1
  1792 00012722 7307                <1> 	jnb	short sb_irq_h1
  1793                              <1> sb_irq_h0:
  1794 00012724 E8A9000000          <1> 	call	sb16_stop
  1795 00012729 EB2B                <1> 	jmp	short sb_irq_h3
  1796                              <1> sb_irq_h1:
  1797                              <1> 	;call	sb16_tuneloop
  1798                              <1> 	; 09/10/2017
  1799                              <1> sb16_tuneloop:
  1800 0001272B 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff]
  1801 00012731 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size]
  1802 00012737 D1E9                <1> 	shr	ecx, 1 ; dma buff size / 2 = half buffer size
  1803                              <1> 
  1804                              <1> 	; 22/05/2017
  1805 00012739 F605[28710100]01    <1> 	test	byte [audio_flag], 1  ; Current flag value
  1806 00012740 7402                <1> 	jz	short sb_tlp1 ; EOL (Half Buffer 1 must be filled)
  1807                              <1> 	; FLAG (Half Buffer 2 must be filled)
  1808 00012742 01CF                <1> 	add	edi, ecx
  1809                              <1> 	; 15/05/2017
  1810                              <1> sb_tlp1: 
  1811 00012744 8B35[18710100]      <1> 	mov	esi, [audio_p_buffer] ; phy addr of audio buff
  1812                              <1> 	;rep	movsb
  1813 0001274A C1E902              <1> 	shr	ecx, 2 ; half buff size / 4
  1814 0001274D F3A5                <1> 	rep	movsd 
  1815                              <1> 	;retn
  1816                              <1> 
  1817                              <1> 	; 10/10/2017
  1818                              <1> 	; switch flag value
  1819 0001274F 8035[28710100]01    <1> 	xor	byte [audio_flag], 1
  1820                              <1> 
  1821                              <1> 	; 12/10/2017
  1822                              <1> 	; [audio_flag] = 0 : Playing dma half buffer 2 (odd intr count)
  1823                              <1> 			   ; Next buffer (to update) is dma half buff 1
  1824                              <1> 	; 	       = 1 : Playing dma half buffer 1 (even intr count)
  1825                              <1> 			   ; Next buffer (to update) is dma half buff 2
  1826                              <1> 
  1827                              <1> sb_irq_h3:
  1828                              <1> 	;mov	byte [audio_busy], 0
  1829                              <1> 
  1830                              <1> 	;pop	edi
  1831                              <1> 	;pop	esi
  1832                              <1> 	;pop	edx
  1833                              <1> 	;pop	ecx
  1834                              <1> 	;pop	ebx ; * must be restored !
  1835                              <1> 	;pop	eax ; * must be restored !
  1836                              <1> 	
  1837 00012756 C3                  <1> 	retn
  1838                              <1> 
  1839                              <1> sb16_volume:
  1840                              <1> 	; 22/10/2017
  1841                              <1> 	; mov [audio_master_volume_l], cl 
  1842                              <1> 	; mov [audio_master_volume_h], ch 
  1843 00012757 66890D[36710100]    <1> 	mov	[audio_master_volume], cx
  1844                              <1> sb16_volume_initial:
  1845 0001275E 6652                <1> 	push	dx ; DX (port address) must be saved
  1846 00012760 668B15[06710100]    <1> 	mov	dx, [audio_io_base]
  1847 00012767 6683C204            <1> 	add	dx, 4 ; Mixer chip address port
  1848 0001276B B022                <1> 	mov	al, 22h ; master volume
  1849 0001276D EE                  <1> 	out	dx, al
  1850 0001276E 6642                <1> 	inc	dx
  1851 00012770 8A25[36710100]      <1> 	mov	ah, [audio_master_volume_l]
  1852 00012776 C0EC02              <1> 	shr	ah, 2 ; 32 -> 8 level
  1853 00012779 C0E405              <1> 	shl	ah, 5 ; bit 5 to 7
  1854 0001277C A0[37710100]        <1> 	mov	al, [audio_master_volume_r]	
  1855 00012781 C0E802              <1> 	shr	al, 2 ; 32 -> 8 level
  1856                              <1> 	;and	al, 0Fh
  1857 00012784 D0E0                <1> 	shl	al, 1 ; bit 1 to 3
  1858 00012786 08E0                <1> 	or	al, ah
  1859 00012788 EE                  <1> 	out	dx, al
  1860 00012789 665A                <1> 	pop	dx ; DX (port address) must be restored
  1861 0001278B C3                  <1> 	retn
  1862                              <1> 
  1863                              <1> sb16_pause:
  1864 0001278C 668B15[06710100]    <1> 	mov	dx, [audio_io_base]
  1865 00012793 6683C20C            <1> 	add	dx, 0Ch ; Command & Data Port
  1866 00012797 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit samples
  1867 0001279E 7404                <1> 	je	short sb_pause_1
  1868                              <1> 	; 8 bit samples
  1869 000127A0 B3D0                <1> 	mov	bl, 0D0h ; 8 bit DMA mode
  1870 000127A2 EB02                <1> 	jmp	short sb_pause_2
  1871                              <1> sb_pause_1:
  1872                              <1> 	; 16 bit samples
  1873 000127A4 B3D5                <1> 	mov	bl, 0D5h ; 16 bit DMA mode
  1874                              <1> sb_pause_2:     
  1875                              <1> 	SbOut   bl ; bCommand
  1875                              <2> %%Wait:
  1875 000127A6 EC                  <2>  in al, dx
  1875 000127A7 08C0                <2>  or al, al
  1875 000127A9 78FB                <2>  js short %%Wait
  1875 000127AB 88D8                <2>  mov al, %1
  1875 000127AD EE                  <2>  out dx, al
  1876                              <1> sb_pause_3:
  1877 000127AE C3                  <1> 	retn
  1878                              <1> 
  1879                              <1> sb16_continue:
  1880 000127AF 668B15[06710100]    <1> 	mov	dx, [audio_io_base]
  1881 000127B6 6683C20C            <1> 	add	dx, 0Ch ; Command & Data Port
  1882 000127BA 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit samples
  1883 000127C1 7404                <1> 	je	short sb_cont_1
  1884                              <1> 	; 8 bit samples
  1885 000127C3 B3D4                <1> 	mov	bl, 0D4h ; 8 bit DMA mode
  1886 000127C5 EB02                <1> 	jmp	short sb_cont_2
  1887                              <1> sb_cont_1:
  1888                              <1> 	; 16 bit samples
  1889 000127C7 B3D6                <1> 	mov	bl, 0D6h ; 16 bit DMA mode
  1890                              <1> sb_cont_2:     
  1891                              <1> 	SbOut   bl ; bCommand
  1891                              <2> %%Wait:
  1891 000127C9 EC                  <2>  in al, dx
  1891 000127CA 08C0                <2>  or al, al
  1891 000127CC 78FB                <2>  js short %%Wait
  1891 000127CE 88D8                <2>  mov al, %1
  1891 000127D0 EE                  <2>  out dx, al
  1892                              <1> sb_cont_3:
  1893 000127D1 C3                  <1> 	retn
  1894                              <1> 
  1895                              <1> sb16_stop:
  1896                              <1> 	; 24/04/2017
  1897 000127D2 803D[34710100]00    <1> 	cmp	byte [audio_play_cmd], 0
  1898 000127D9 7648                <1> 	jna	short sb16_stop_4
  1899                              <1> 
  1900                              <1> 	; 22/05/2017
  1901 000127DB 668B15[06710100]    <1> 	mov	dx, [audio_io_base]
  1902 000127E2 6683C20C            <1> 	add	dx, 0Ch
  1903                              <1> 
  1904 000127E6 B3D9                <1> 	mov	bl, 0D9h ; exit auto-initialize 16 bit transfer
  1905                              <1> 	; stop  autoinitialized DMA transfer mode 
  1906 000127E8 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit samples
  1907 000127EF 7402                <1> 	je	short sb16_stop_1
  1908                              <1> 	;mov	bl, 0DAh ; exit auto-initialize 8 bit transfer
  1909 000127F1 FEC3                <1> 	inc	bl
  1910                              <1> sb16_stop_1:
  1911                              <1> 	SbOut	bl ; exit auto-initialize transfer command
  1911                              <2> %%Wait:
  1911 000127F3 EC                  <2>  in al, dx
  1911 000127F4 08C0                <2>  or al, al
  1911 000127F6 78FB                <2>  js short %%Wait
  1911 000127F8 88D8                <2>  mov al, %1
  1911 000127FA EE                  <2>  out dx, al
  1912                              <1> 
  1913 000127FB 30C0                <1> 	xor     al, al ; stops all DMA processes on selected channel
  1914                              <1> 
  1915 000127FD 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16 ; 16 bit samples
  1916 00012804 7404                <1> 	je	short sb16_stop_2
  1917 00012806 E60C                <1> 	out	0Ch, al ; clear selected channel register
  1918 00012808 EB02                <1> 	jmp	short sb16_stop_3
  1919                              <1> 
  1920                              <1> sb16_stop_2:
  1921 0001280A E6D8                <1> 	out	0D8h, al ; clear selected channel register
  1922                              <1> 
  1923                              <1> sb16_stop_3:
  1924 0001280C C605[34710100]00    <1> 	mov	byte [audio_play_cmd], 0 ; stop !
  1925                              <1> SbDone:
  1926                              <1> 	;mov	dx, [audio_io_base]
  1927                              <1> 	;add	dx, 0Ch
  1928                              <1> 	SbOut   0D0h
  1928                              <2> %%Wait:
  1928 00012813 EC                  <2>  in al, dx
  1928 00012814 08C0                <2>  or al, al
  1928 00012816 78FB                <2>  js short %%Wait
  1928 00012818 B0D0                <2>  mov al, %1
  1928 0001281A EE                  <2>  out dx, al
  1929                              <1> 	SbOut   0D3h
  1929                              <2> %%Wait:
  1929 0001281B EC                  <2>  in al, dx
  1929 0001281C 08C0                <2>  or al, al
  1929 0001281E 78FB                <2>  js short %%Wait
  1929 00012820 B0D3                <2>  mov al, %1
  1929 00012822 EE                  <2>  out dx, al
  1930                              <1> sb16_stop_4:
  1931 00012823 C3                  <1> 	retn
  1932                              <1> 
  1933                              <1> sb16_reset:
  1934                              <1> 	; 24/04/2017      
  1935 00012824 668B15[06710100]    <1> 	mov     dx, [audio_io_base] ; try to reset the DSP.
  1936 0001282B 6683C206            <1> 	add     dx, 06h
  1937 0001282F B001                <1> 	mov	al, 1
  1938 00012831 EE                  <1> 	out	dx, al
  1939                              <1> 
  1940 00012832 EC                  <1> 	in	al, dx
  1941 00012833 EC                  <1> 	in	al, dx
  1942 00012834 EC                  <1> 	in	al, dx
  1943 00012835 EC                  <1> 	in	al, dx
  1944                              <1> 
  1945 00012836 30C0                <1> 	xor     al, al
  1946 00012838 EE                  <1> 	out	dx, al
  1947                              <1> 
  1948 00012839 6683C208            <1> 	add     dx, 08h
  1949 0001283D 66B96400            <1> 	mov	cx, 100
  1950                              <1> sbrstWaitID:
  1951 00012841 EC                  <1> 	in	al, dx
  1952 00012842 08C0                <1> 	or      al, al
  1953 00012844 7804                <1> 	js      short sbrstGetID
  1954 00012846 E2F9                <1> 	loop    sbrstWaitID
  1955 00012848 F9                  <1> 	stc
  1956 00012849 C3                  <1> 	retn
  1957                              <1> sbrstGetID:          
  1958 0001284A 6683EA04            <1> 	sub     dx, 04h
  1959 0001284E EC                  <1> 	in	al, dx
  1960 0001284F 3CAA                <1> 	cmp     al, 0AAh
  1961 00012851 7406                <1> 	je      short sb_rst_retn
  1962 00012853 6683C204            <1> 	add     dx, 04h
  1963 00012857 E2E8                <1> 	loop    sbrstWaitID
  1964                              <1> sb_rst_retn:
  1965 00012859 C3                  <1> 	retn
  1966                              <1> 
  1967                              <1> ac97_codec_config:
  1968                              <1> 	; 10/06/2017
  1969                              <1> 	; 05/06/2017
  1970                              <1> 	; 29/05/2017
  1971                              <1> 	; 28/05/2017 (TRDOS 386, 'audio.s')
  1972                              <1> 	; 07/11/2016 (Erdogan Tan)
  1973                              <1> 	; Derived from 'codecConfig' procedure in 'CODEC.ASM'
  1974                              <1> 	; .wav player for DOS by Jeff Leyda (02/09/2002)
  1975                              <1> 
  1976                              <1> 	;; 'PLAYER.ASM'
  1977                              <1> 	;; get ICH base address regs for mixer and bus master
  1978                              <1> 
  1979                              <1> init_ac97_controller: ; 10/06/2017
  1980 0001285A A1[08710100]        <1> 	mov	eax, [audio_dev_id]
  1981                              <1>         ;mov	al, NAMBAR_REG
  1982                              <1>         ;;call  pciRegRead16			; read PCI registers 10-11
  1983                              <1>         ;call	pciRegRead32
  1984                              <1> 	;and	dx, IO_ADDR_MASK 		; mask off BIT0
  1985                              <1> 	;;and	edx, IO_ADDR_MASK 
  1986                              <1> 
  1987                              <1>         ;mov	[NAMBAR], dx			; save audio mixer base addr
  1988                              <1> 
  1989                              <1>         ;mov    al, NABMBAR_REG
  1990                              <1>         ;;call	pciRegRead16
  1991                              <1>         ;call	pciRegRead32
  1992                              <1> 	;and	dx, 0FFC0h ; IO_ADDR_MASK
  1993                              <1> 	;;and	edx, 0FFC0h
  1994                              <1> 
  1995                              <1>         ;mov    [NABMBAR], dx			; save bus master base addr
  1996                              <1> 
  1997                              <1> 	;mov	eax, [audio_dev_id]
  1998 0001285F B004                <1>         mov     al, PCI_CMD_REG
  1999                              <1>         ;call	pciRegRead8			; read PCI command register
  2000 00012861 E84AF8FFFF          <1>         call	pciRegRead16
  2001 00012866 80CA05              <1> 	or      dl, IO_ENA+BM_ENA               ; enable IO and bus master
  2002                              <1>         ;call 	pciRegWrite8
  2003 00012869 E8ADF8FFFF          <1> 	call	pciRegWrite16
  2004                              <1> 
  2005                              <1> 	; 'CODEC.ASM'
  2006                              <1> 
  2007                              <1> 	; enable codec, unmute stuff, set output rate
  2008                              <1> ;	; entry: [audio_freq] = desired sample rate
  2009                              <1> 		
  2010                              <1> ;	mov    	dx, [NAMBAR]               	
  2011                              <1> ;	add    	dx, CODEC_EXT_AUDIO_CTRL_REG  	; 2Ah  	  
  2012                              <1> ;	in     	ax, dx
  2013                              <1> ;	or	ax, 1
  2014                              <1> ;	out	dx, ax 				; Enable variable rate audio
  2015                              <1> 
  2016                              <1> ;       ;call    delay1_4ms
  2017                              <1> ;       ;call    delay1_4ms
  2018                              <1> ;       ;call    delay1_4ms
  2019                              <1> ;       ;call    delay1_4ms
  2020                              <1> 
  2021                              <1> ;	mov	ax, [audio_freq]		; sample rate
  2022                              <1> 
  2023                              <1> ;	mov    	dx, [NAMBAR]               	
  2024                              <1> ;	add    	dx, CODEC_PCM_FRONT_DACRATE_REG	; 2Ch  	  
  2025                              <1> ;	out	dx, ax 				; out sample rate
  2026                              <1> 		
  2027                              <1> ;       ;call	delay1_4ms
  2028                              <1> ;       ;call	delay1_4ms
  2029                              <1> ;       ;call	delay1_4ms
  2030                              <1> ;       ;call	delay1_4ms
  2031                              <1> 
  2032                              <1> 	;mov	dx, [NAMBAR]			; mixer base address
  2033                              <1>         ;add	dx, CODEC_RESET_REG  		; reset register
  2034                              <1>         ;mov	ax, 42
  2035                              <1> 	;out	dx, ax                          ; reset
  2036                              <1> 
  2037                              <1> 	;mov    dx, [NABMBAR]			; bus master base address
  2038                              <1>         ;add	dx, GLOB_STS_REG
  2039                              <1>         ;mov	ax, 2
  2040                              <1> 	;out	dx, ax                         
  2041                              <1> 
  2042 0001286E E847F9FFFF          <1>         call    delay_100ms ; 29/05/2017
  2043                              <1> 
  2044                              <1> init_ac97_codec:
  2045                              <1> 	; 10/06/2017
  2046                              <1> 	; 29/05/2017
  2047                              <1> 	; 28/05/2017 - Erdogan Tan (Ref: KolibriOS, intelac97.asm)
  2048                              <1> 	;	
  2049 00012873 66BA2C00            <1> 	mov	dx, GLOB_CNT_REG ; 2Ch
  2050 00012877 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2051 0001287E ED                  <1> 	in	eax, dx
  2052                              <1> 	; ?
  2053 0001287F 66BA3000            <1> 	mov	dx, GLOB_STS_REG ; 30h
  2054 00012883 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2055 0001288A ED                  <1> 	in	eax, dx
  2056                              <1> 
  2057 0001288B 83F8FF              <1> 	cmp	eax, 0FFFFFFFFh ; -1
  2058 0001288E 744B                <1> 	je	short init_ac97_codec_err1
  2059                              <1> 
  2060 00012890 A900030010          <1> 	test	eax, CTRL_ST_CREADY
  2061 00012895 7507                <1> 	jnz	short _ac97_codec_ready
  2062                              <1> 
  2063 00012897 E8EF020000          <1> 	call	reset_ac97_codec
  2064 0001289C 723E                <1> 	jc	short init_ac97_codec_err2
  2065                              <1> 
  2066                              <1> _ac97_codec_ready:
  2067 0001289E 668B15[38710100]    <1> 	mov	dx, [NAMBAR]
  2068                              <1> 	;add	dx, 0 ; ac_reg_0 ; reset register
  2069 000128A5 66EF                <1> 	out	dx, ax
  2070                              <1> 
  2071 000128A7 31C0                <1> 	xor	eax, eax ; 0
  2072 000128A9 668B15[38710100]    <1> 	mov	dx, [NAMBAR]
  2073 000128B0 6683C226            <1> 	add	dx, CODEC_REG_POWERDOWN	
  2074 000128B4 66EF                <1> 	out	dx, ax
  2075                              <1> 
  2076                              <1> 	; 10/06/2017
  2077                              <1> 	; 29/05/2017
  2078                              <1> 	; wait for 1 second
  2079 000128B6 B9E8030000          <1> 	mov	ecx, 1000 ; 1000*0.25ms = 1s
  2080                              <1> _ac97_codec_rloop:
  2081 000128BB E807F9FFFF          <1> 	call	delay1_4ms
  2082 000128C0 E802F9FFFF          <1> 	call	delay1_4ms
  2083 000128C5 E8FDF8FFFF          <1> 	call	delay1_4ms
  2084 000128CA E8F8F8FFFF          <1> 	call	delay1_4ms
  2085                              <1> 	;mov	dx, [NAMBAR]
  2086                              <1> 	;add	dx, CODEC_REG_POWERDOWN
  2087 000128CF 66ED                <1> 	in	ax, dx	
  2088 000128D1 6683E00F            <1> 	and	ax, 0Fh
  2089 000128D5 3C0F                <1> 	cmp	al, 0Fh
  2090 000128D7 7404                <1> 	je	short _ac97_codec_init_ok
  2091 000128D9 E2E0                <1> 	loop	_ac97_codec_rloop 
  2092                              <1> 
  2093                              <1> init_ac97_codec_err1:
  2094 000128DB F9                  <1> 	stc
  2095                              <1> init_ac97_codec_err2:
  2096 000128DC C3                  <1> 	retn
  2097                              <1> 
  2098                              <1> _ac97_codec_init_ok:
  2099 000128DD B002                <1>         mov     al, 2 ; force set 16-bit 2-channel PCM
  2100 000128DF 66BA2C00            <1> 	mov	dx, GLOB_CNT_REG ; 2Ch
  2101 000128E3 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2102 000128EA EF                  <1> 	out	dx, eax
  2103                              <1> 
  2104                              <1> 	;call	delay1_4ms
  2105                              <1> 
  2106                              <1> 	; 10/06/2017
  2107 000128EB E849020000          <1> 	call 	reset_ac97_controller
  2108                              <1> 
  2109                              <1> ;	call 	setup_ac97_codec
  2110                              <1> ;
  2111                              <1> ;detect_ac97_codec:
  2112                              <1> ;	retn
  2113                              <1> 
  2114                              <1> setup_ac97_codec:
  2115                              <1> 	; 22/07/2020
  2116                              <1> 	; 10/06/2017
  2117                              <1> 	; 29/05/2017
  2118 000128F0 B802020000          <1> 	mov     eax, 0202h
  2119 000128F5 66A3[36710100]      <1> 	mov	[audio_master_volume], ax
  2120 000128FB 66B81F1F            <1> 	mov	ax, 1F1Fh ; 31, 31
  2121                              <1> 	
  2122 000128FF 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2123 00012906 6683C202            <1>   	add     dx, CODEC_MASTER_VOL_REG	;02h 
  2124 0001290A 6631C0              <1>   	xor	ax, ax 	; volume attenuation = 0 (max. volume)
  2125 0001290D 66EF                <1>   	out     dx, ax
  2126                              <1>  
  2127 0001290F 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2128 00012916 6683C206            <1>   	add     dx, CODEC_MASTER_MONO_VOL_REG	;06h 
  2129                              <1> 	;xor	ax, ax
  2130 0001291A 66EF                <1>   	out     dx, ax
  2131                              <1> 
  2132 0001291C 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2133 00012923 6683C20A            <1>   	add     dx, CODEC_PCBEEP_VOL_REG	;0Ah 
  2134                              <1>   	;xor    ax, ax
  2135 00012927 66EF                <1>   	out     dx, ax
  2136                              <1> 
  2137 00012929 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2138 00012930 6683C218            <1>   	add     dx, CODEC_PCM_OUT_REG		;18h 
  2139                              <1>   	;xor    ax, ax
  2140 00012934 66EF                <1>   	out     dx, ax
  2141                              <1> 
  2142 00012936 66B80880            <1> 	mov     ax, 8008h ; Mute
  2143 0001293A 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2144                              <1> 	; 22/07/2020
  2145 00012941 6683C20C            <1> 	add	dx, CODEC_PHONE_VOL_REG		;0Ch
  2146                              <1> 				 ; AC97_PHONE_VOL ; TAD Input (Mono)
  2147 00012945 66EF                <1>   	out     dx, ax
  2148                              <1> 
  2149 00012947 66B80808            <1>         mov	ax, 0808h
  2150 0001294B 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2151 00012952 6683C210            <1>         add	dx, CODEC_LINE_IN_VOL_REG ;10h ; Line Input (Stereo)	
  2152 00012956 66EF                <1>   	out     dx, ax
  2153                              <1> 
  2154                              <1> 	;mov	ax, 0808h
  2155 00012958 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2156 0001295F 6683C212            <1>         add	dx, CODEC_CD_VOL_REG ;12h ; CR Input (Stereo)
  2157 00012963 66EF                <1>   	out     dx, ax
  2158                              <1> 
  2159                              <1> 	;mov	ax, 0808h
  2160 00012965 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2161 0001296C 6683C216            <1>         add	dx, CODEC_AUX_VOL_REG ;16h ; Aux Input (Stereo)
  2162 00012970 66EF                <1>   	out     dx, ax
  2163                              <1> 
  2164                              <1>         ;call    delay1_4ms
  2165                              <1>         ;call    delay1_4ms
  2166                              <1>         ;call    delay1_4ms
  2167                              <1>         ;call    delay1_4ms
  2168                              <1> 
  2169                              <1> detect_ac97_codec:
  2170 00012972 C3                  <1>         retn
  2171                              <1> 
  2172                              <1> set_ac97_bdl: ; Set AC97 (ICH) Buffer Descriptor List
  2173                              <1> 	; 17/06/2017
  2174                              <1> 	; 11/06/2017
  2175                              <1> 	; 28/05/2017
  2176                              <1> 	; eax = dma buffer address = [audio_DMA_buff]
  2177                              <1> 	; ecx = dma buffer buffer size = [audio_dmabuff_size]
  2178                              <1> 
  2179 00012973 D1E9                <1> 	shr	ecx, 1 ; dma half buffer size
  2180 00012975 89CE                <1> 	mov	esi, ecx
  2181                              <1> 
  2182 00012977 BF[3C710100]        <1>         mov     edi, audio_bdl_buff	; get BDL address
  2183 0001297C B910000000          <1>         mov     ecx, 32 / 2		; make 32 entries in BDL
  2184                              <1> 
  2185 00012981 EB05                <1> 	jmp	short s_ac97_bdl1 
  2186                              <1> 
  2187                              <1> s_ac97_bdl0:
  2188                              <1> 	; set buffer descriptor 0 to start of data file in memory
  2189                              <1> 
  2190 00012983 A1[20710100]        <1>  	mov	eax, [audio_dma_buff]	; Physical address of DMA buffer
  2191                              <1>  
  2192                              <1> s_ac97_bdl1:
  2193 00012988 AB                  <1> 	stosd				; store dmabuffer1 address
  2194                              <1> 
  2195 00012989 89C2                <1> 	mov	edx, eax
  2196                              <1> 
  2197                              <1> ;
  2198                              <1> ; Buffer Descriptors List
  2199                              <1> ; As stated earlier, each buffer descriptor list is a set of (up to) 32 
  2200                              <1> ; descriptors, each 8 bytes in length. Bytes 0-3 of a descriptor entry point
  2201                              <1> ; to a chunk of memory to either play from or record to. Bytes 4-7 of an
  2202                              <1> ; entry describe various control things detailed below.
  2203                              <1> ; 
  2204                              <1> ; Buffer pointers must always be aligned on a Dword boundry.
  2205                              <1> ;
  2206                              <1> ;
  2207                              <1> 
  2208                              <1> ;IOC                     equ     BIT31	; Fire an interrupt whenever this
  2209                              <1>                                         ; buffer is complete.
  2210                              <1> 
  2211                              <1> ;BUP                     equ     BIT30  ; Buffer Underrun Policy.
  2212                              <1>                                         ; if this buffer is the last buffer
  2213                              <1>                                         ; in a playback, fill the remaining
  2214                              <1>                                         ; samples with 0 (silence) or not.
  2215                              <1>                                         ; It's a good idea to set this to 1
  2216                              <1>                                         ; for the last buffer in playback,
  2217                              <1>                                         ; otherwise you're likely to get a lot
  2218                              <1>                                         ; of noise at the end of the sound.
  2219                              <1> 
  2220                              <1> ;
  2221                              <1> ; Bits 15:0 contain the length of the buffer, in number of samples, which
  2222                              <1> ; are 16 bits each, coupled in left and right pairs, or 32bits each.
  2223                              <1> ; Luckily for us, that's the same format as .wav files.
  2224                              <1> ;
  2225                              <1> ; A value of FFFF is 65536 samples. Running at 44.1Khz, that's just about
  2226                              <1> ; 1.5 seconds of sample time. FFFF * 32bits is 1FFFFh bytes or 128k of data.
  2227                              <1> ;
  2228                              <1> ; A value of 0 in these bits means play no samples.
  2229                              <1> ;
  2230                              <1> 
  2231 0001298B 89F0                <1> 	mov	eax, esi ; DMA half buffer size
  2232 0001298D 01C2                <1> 	add	edx, eax
  2233 0001298F D1E8                <1> 	shr	eax, 1 ; count of 16 bit samples
  2234                              <1> 	;or	eax, IOC+BUP
  2235 00012991 0D00000080          <1> 	or	eax, IOC ; 11/06/2017
  2236 00012996 AB                  <1> 	stosd
  2237                              <1> 
  2238                              <1> ; 2nd buffer:
  2239                              <1> 
  2240 00012997 89D0                <1>         mov	eax, edx ; Physical address of the 2nd half of DMA buffer	
  2241 00012999 AB                  <1> 	stosd		 ; store dmabuffer2 address
  2242                              <1> 
  2243                              <1> ; set length to [audio_dmabuff_size]/2
  2244                              <1> ; Set control (bits 31:16) to BUP, bits 15:0=number of samples
  2245                              <1> ; 
  2246 0001299A 89F0                <1> 	mov	eax, esi ; DMA half buffer size
  2247 0001299C D1E8                <1> 	shr	eax, 1 ; count of 16 bit samples
  2248                              <1> 	;or	eax, IOC+BUP
  2249 0001299E 0D00000080          <1> 	or	eax, IOC ; 11/06/2017
  2250 000129A3 AB                  <1> 	stosd
  2251                              <1> 
  2252 000129A4 E2DD                <1> 	loop    s_ac97_bdl0
  2253                              <1> 	
  2254 000129A6 C3                  <1> 	retn
  2255                              <1> 
  2256                              <1> ac97_start_play:  
  2257                              <1> 	; 28/05/2017
  2258                              <1> 	; Derived from 'playWav' procedure in 'ICHWAV.ASM'
  2259                              <1> 	; .wav player for DOS by Jeff Leyda (02/09/2002)
  2260                              <1> 
  2261                              <1> 	; set output rate
  2262                              <1> 	; entry: [audio_freq] = desired sample rate
  2263                              <1> 		
  2264 000129A7 668B15[38710100]    <1> 	mov    	dx, [NAMBAR]               	
  2265 000129AE 6683C22A            <1> 	add    	dx, CODEC_EXT_AUDIO_CTRL_REG  	; 2Ah  	  
  2266 000129B2 66ED                <1> 	in     	ax, dx
  2267 000129B4 6683C801            <1> 	or	ax, 1
  2268 000129B8 66EF                <1> 	out	dx, ax 				; Enable variable rate audio
  2269                              <1> 
  2270                              <1>        ;call    delay1_4ms
  2271                              <1>        ;call    delay1_4ms
  2272                              <1>        ;call    delay1_4ms
  2273                              <1>        ;call    delay1_4ms
  2274                              <1> 
  2275 000129BA 66A1[32710100]      <1> 	mov	ax, [audio_freq]		; sample rate
  2276                              <1> 
  2277 000129C0 668B15[38710100]    <1> 	mov    	dx, [NAMBAR]               	
  2278 000129C7 6683C22C            <1> 	add    	dx, CODEC_PCM_FRONT_DACRATE_REG	; 2Ch  	  
  2279 000129CB 66EF                <1> 	out	dx, ax 				; out sample rate
  2280                              <1> 		
  2281                              <1>        ;call    delay1_4ms
  2282                              <1>        ;call    delay1_4ms
  2283                              <1>        ;call    delay1_4ms
  2284                              <1>        ;call    delay1_4ms
  2285                              <1> 
  2286                              <1> ;
  2287                              <1> ; register reset the DMA engine. This may cause a pop noise on the output
  2288                              <1> ; lines when the device is reset. Prolly a better idea to mute output, then
  2289                              <1> ; reset.
  2290                              <1> ;
  2291 000129CD 668B15[3A710100]    <1>         mov     dx, [NABMBAR]
  2292 000129D4 6683C21B            <1>         add     dx, PO_CR_REG                  ; set pointer to Cntl reg
  2293 000129D8 B002                <1>         mov     al, RR                         ; set reset
  2294 000129DA EE                  <1>         out     dx, al                         ; self clearing bit
  2295                              <1> ;
  2296                              <1> ;	mov	edi, audio_bdl_buff
  2297                              <1> ;	mov	edx, [audio_dmabuff_size]
  2298                              <1> ;	shr	edx, 1
  2299                              <1> ;	mov	ecx, 32/2
  2300                              <1> ;ac97_set_bdl_buffer:
  2301                              <1> ;	; 1st half of DMA buffer
  2302                              <1> ;	mov	eax, [audio_dma_buff]
  2303                              <1> ;	push	eax
  2304                              <1> ;	stosd
  2305                              <1> ;	mov	eax, edx ; dma buffer size / 2
  2306                              <1> ;	or	eax, IOC+BUP
  2307                              <1> ;	stosd
  2308                              <1> ;	pop	eax
  2309                              <1> ;	; 2nd half of DMA buffer
  2310                              <1> ;	add	eax, edx
  2311                              <1> ;	stosd
  2312                              <1> ;	mov	eax, edx ; dma buffer size / 2
  2313                              <1> ;	or	eax, IOC+BUP
  2314                              <1> ;	stosd
  2315                              <1> ;	loop	ac97_set_bdl_buffer
  2316                              <1>  	
  2317                              <1> ; tell the DMA engine where to find our list of Buffer Descriptors.
  2318                              <1> ; this 32bit value is a flat mode memory offset (ie no segment:offset)
  2319                              <1> ;
  2320                              <1> ; write NABMBAR+10h with offset of buffer descriptor list
  2321                              <1> ;
  2322 000129DB B8[3C710100]        <1>         mov	eax, audio_bdl_buff
  2323 000129E0 668B15[3A710100]    <1> 	mov	dx, [NABMBAR]
  2324 000129E7 6683C210            <1> 	add	dx, PO_BDBAR_REG
  2325 000129EB EF                  <1> 	out	dx, eax
  2326                              <1> ;
  2327                              <1> ; All set. Let's play some music.
  2328                              <1> ;
  2329                              <1> ;
  2330 000129EC B81F000000          <1> 	mov	eax, 31
  2331 000129F1 E816000000          <1> 	call    set_ac97_LastValidIndex
  2332                              <1> 
  2333 000129F6 C605[34710100]01    <1> 	mov	byte [audio_play_cmd], 1 ; play command (do not stop) !
  2334                              <1> 
  2335                              <1> ac97_play: ; continue to play (after pause)
  2336                              <1> 	; 11/06/2017
  2337                              <1> 	; 29/05/2017
  2338                              <1> 	; 28/05/2017
  2339 000129FD 668B15[3A710100]    <1>         mov     dx, [NABMBAR]
  2340 00012A04 6683C21B            <1>         add     dx, PO_CR_REG		; PCM out control register
  2341 00012A08 B011                <1>         mov	al, IOCE+RPBM ; 29/05/2017
  2342                              <1>         ;mov	al, 1Dh ; (Ref: KolibriOS, intelac97.asm, 'play:')
  2343 00012A0A EE                  <1> 	out     dx, al			; set start!
  2344                              <1> 
  2345                              <1> 	;mov	byte [audio_play_cmd], 1 ; play command (do not stop) !
  2346                              <1> 
  2347 00012A0B C3                  <1> 	retn
  2348                              <1> 
  2349                              <1> ;input AL = index # to stop on
  2350                              <1> set_ac97_LastValidIndex:
  2351                              <1> 	; 28/05/2017
  2352                              <1> 	; Derived from 'setLastValidIndex' procedure in 'ICHWAV.ASM'
  2353                              <1> 	; .wav player for DOS by Jeff Leyda (02/09/2002)
  2354 00012A0C 668B15[3A710100]    <1> 	mov	dx, [NABMBAR]
  2355 00012A13 6683C215            <1> 	add	dx, PO_LVI_REG
  2356 00012A17 EE                  <1>         out     dx, al
  2357                              <1> 	;mov	[audio_lvi], al ; for ac97_int_handler
  2358 00012A18 C3                  <1> 	retn
  2359                              <1> 
  2360                              <1> ac97_volume:
  2361                              <1> 	; 28/05/2017
  2362                              <1> 	; bl = component (0 = master/playback/lineout volume)
  2363                              <1> 	; cl = left channel volume level (0 to 31)
  2364                              <1> 	; ch = right channel volume level (0 to 31)
  2365                              <1> 
  2366 00012A19 08DB                <1> 	or	bl, bl
  2367 00012A1B 7523                <1> 	jnz	short ac97_vol_1 ; temporary !
  2368 00012A1D 66B81F1F            <1> 	mov	ax, 1F1Fh ; 31,31
  2369 00012A21 38C1                <1> 	cmp	cl, al
  2370 00012A23 771B                <1> 	ja	short ac97_vol_1 ; temporary !
  2371 00012A25 38E5                <1> 	cmp	ch, ah
  2372 00012A27 7717                <1> 	ja	short ac97_vol_1 ; temporary !
  2373 00012A29 66890D[36710100]    <1> 	mov	[audio_master_volume], cx
  2374 00012A30 6629C8              <1> 	sub	ax, cx
  2375 00012A33 668B15[38710100]    <1>   	mov     dx, [NAMBAR]
  2376 00012A3A 6683C202            <1>   	add     dx, CODEC_MASTER_VOL_REG  ; 02h ; Line Out 
  2377 00012A3E 66EF                <1>   	out     dx, ax
  2378                              <1> ac97_vol_1:
  2379 00012A40 C3                  <1> 	retn
  2380                              <1> 
  2381                              <1> ac97_int_handler:
  2382                              <1> 	; 12/10/2017
  2383                              <1> 	; 10/10/2017
  2384                              <1> 	; 09/10/2017
  2385                              <1> 	; 13/06/2017, 13/06/2017
  2386                              <1> 	; 10/06/2017, 11/06/2017
  2387                              <1> 	; Interrupt Handler for AC97 (ICH) Audio Controller
  2388                              <1> 	; Note: called by 'dev_IRQ_service' 
  2389                              <1> 	; 28/05/2017
  2390                              <1> 
  2391                              <1> 	;push	eax ; * must be saved !
  2392                              <1> 	;push	edx
  2393                              <1> 	;push	ecx
  2394                              <1> 	;push	ebx ; * must be saved !
  2395                              <1> 	;push	esi
  2396                              <1> 	;push	edi
  2397                              <1> 
  2398                              <1> 	;cmp	byte [audio_busy], 1
  2399                              <1> 	;jnb	_ac97_ih2	; busy !
  2400                              <1> 
  2401 00012A41 66BA3000            <1>         mov     dx, GLOB_STS_REG
  2402 00012A45 660315[3A710100]    <1>         add	dx, [NABMBAR]
  2403 00012A4C ED                  <1> 	in	eax, dx
  2404                              <1> 
  2405 00012A4D 83F8FF              <1>         cmp     eax, 0FFFFFFFFh ; -1
  2406 00012A50 0F849A000000        <1>         je      _ac97_ih3 ; exit
  2407                              <1> 
  2408 00012A56 A940000000          <1>         test    eax, 40h ; PCM Out Interrupt
  2409 00012A5B 750E                <1>         jnz     short _ac97_ih0
  2410                              <1> 
  2411 00012A5D 85C0                <1> 	test	eax, eax
  2412 00012A5F 0F848B000000        <1> 	jz	_ac97_ih3 ; exit
  2413                              <1> 
  2414                              <1>  	;mov	dx, GLOB_STS_REG
  2415                              <1>         ;add	dx, [NABMBAR]
  2416 00012A65 EF                  <1> 	out	dx, eax
  2417                              <1> 
  2418 00012A66 E985000000          <1> 	jmp	_ac97_ih3 ; exit
  2419                              <1> 
  2420                              <1> _ac97_ih0:
  2421 00012A6B 50                  <1> 	push	eax
  2422                              <1> 	; 09/10/2017
  2423 00012A6C 803D[34710100]01    <1> 	cmp	byte [audio_play_cmd], 1
  2424 00012A73 727C                <1> 	jb	short _ac97_ih4 ; stop command !
  2425                              <1> 
  2426                              <1> 	;mov	byte [audio_busy], 1
  2427                              <1> 
  2428                              <1> 	;mov	al, 10h
  2429                              <1> 	;mov	dx, PO_CR_REG
  2430                              <1>         ;add	dx, [NABMBAR]
  2431                              <1> 	;out	dx, al
  2432                              <1> 
  2433 00012A75 66B81C00            <1> 	mov	ax, 1Ch ; FIFOE(=16)+BCIS(=8)+LVBCI(=4)
  2434 00012A79 66BA1600            <1> 	mov	dx, PO_SR_REG
  2435 00012A7D 660315[3A710100]    <1>         add	dx, [NABMBAR]
  2436 00012A84 66EF                <1> 	out	dx, ax
  2437                              <1> 
  2438 00012A86 66BA1400            <1> 	mov	dx, PO_CIV_REG
  2439 00012A8A 660315[3A710100]    <1>         add	dx, [NABMBAR]
  2440 00012A91 EC                  <1> 	in	al, dx
  2441                              <1> 
  2442                              <1> 	;cmp	al, [audio_civ] ; [audio_flag]
  2443                              <1> 	;je	short _ac97_ih2
  2444                              <1> 
  2445 00012A92 A2[35710100]        <1> 	mov	[audio_civ], al
  2446 00012A97 FEC8                <1> 	dec	al
  2447                              <1> 	;inc	al ; 11/06/2017
  2448 00012A99 241F                <1> 	and	al, 1Fh
  2449                              <1> 
  2450 00012A9B 66BA1500            <1>         mov     dx, PO_LVI_REG
  2451 00012A9F 660315[3A710100]    <1>         add	dx, [NABMBAR]
  2452 00012AA6 EE                  <1>         out	dx, al
  2453                              <1> 
  2454                              <1> 	; 12/10/2017
  2455 00012AA7 A0[35710100]        <1> 	mov	al, [audio_civ]
  2456 00012AAC FEC0                <1> 	inc	al
  2457 00012AAE 2401                <1> 	and	al, 1
  2458 00012AB0 A2[28710100]        <1> 	mov	[audio_flag], al 
  2459                              <1> 	;; [audio_flag] : 0 = Buffer 1, 1 = Buffer 2
  2460                              <1> 	;
  2461 00012AB5 58                  <1> 	pop	eax
  2462                              <1> 	;
  2463 00012AB6 83E040              <1> 	and     eax, 40h
  2464 00012AB9 668B15[3A710100]    <1>         mov	dx, [NABMBAR]
  2465 00012AC0 6683C230            <1> 	add	dx, GLOB_STS_REG
  2466 00012AC4 EF                  <1> 	out	dx, eax
  2467                              <1> 
  2468                              <1> 	;; 13/06/2017
  2469                              <1> 	;mov	al, 11h ; IOCE + RPBM
  2470                              <1> 	;mov	dx, PO_CR_REG
  2471                              <1>         ;add	dx, [NABMBAR]
  2472                              <1> 	;out	dx, al
  2473                              <1> 
  2474                              <1> ac97_tuneloop:
  2475                              <1> 	; 09/10/2017
  2476 00012AC5 8B3D[20710100]      <1> 	mov	edi, [audio_dma_buff]
  2477 00012ACB 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size]
  2478 00012AD1 D1E9                <1> 	shr	ecx, 1 ; dma buff size / 2 = half buffer size
  2479                              <1> 
  2480                              <1> 	; 12/10/2017
  2481 00012AD3 803D[28710100]00    <1> 	cmp 	byte [audio_flag], 0
  2482 00012ADA 7702                <1> 	ja	short _ac97_ih1  ; Playing Half Buffer 2 (Current: FLAG)
  2483                              <1> 	; Playing Half Buffer 1 (Current: EOL)	
  2484 00012ADC 01CF                <1> 	add	edi, ecx
  2485                              <1> _ac97_ih1: 
  2486                              <1> 	; Update half buffer 2 while playing half buffer 1 (next: FLAG)
  2487                              <1> 	; Update half buffer 1 while playing half buffer 2 (next: EOL)
  2488                              <1> 
  2489 00012ADE 8B35[18710100]      <1> 	mov	esi, [audio_p_buffer] ; phy addr of audio buff
  2490 00012AE4 C1E902              <1> 	shr	ecx, 2 ; half buff size / 4
  2491 00012AE7 F3A5                <1> 	rep	movsd 
  2492                              <1> 
  2493                              <1> 	; 10/10/2017
  2494                              <1> 	; switch flag value
  2495 00012AE9 8035[28710100]01    <1> 	xor	byte [audio_flag], 1
  2496                              <1> 	; 12/10/2017
  2497                              <1> 	; [audio_flag] = 0 : Playing dma half buffer 2 (even index value)
  2498                              <1> 			   ; Next buffer (to update) is dma half buff 1
  2499                              <1> 	; 	       = 1 : Playing dma half buffer 1 (odd index value)
  2500                              <1> 			   ; Next buffer (to update) is dma half buff 2
  2501                              <1> 
  2502                              <1> _ac97_ih2:
  2503                              <1> 	;mov	byte [audio_busy], 0
  2504                              <1> _ac97_ih3:
  2505                              <1> 	;pop	edi
  2506                              <1> 	;pop	esi
  2507                              <1> 	;pop	ebx ; * must be restored !
  2508                              <1> 	;pop	ecx
  2509                              <1> 	;pop	edx
  2510                              <1> 	;pop	eax ; * must be restored !
  2511                              <1> 
  2512 00012AF0 C3                  <1> 	retn
  2513                              <1> 
  2514                              <1> _ac97_ih4:
  2515                              <1> 	; 09/10/2017
  2516 00012AF1 E818000000          <1> 	call	_ac97_stop
  2517                              <1> 	;
  2518 00012AF6 58                  <1> 	pop	eax
  2519                              <1> 	;
  2520 00012AF7 83E040              <1> 	and     eax, 40h
  2521 00012AFA 668B15[3A710100]    <1>         mov	dx, [NABMBAR]
  2522 00012B01 6683C230            <1> 	add	dx, GLOB_STS_REG
  2523 00012B05 EF                  <1> 	out	dx, eax
  2524                              <1> 
  2525                              <1> 	;; 13/06/2017
  2526                              <1> 	;mov	al, 11h ; IOCE + RPBM
  2527                              <1> 	;dx, PO_CR_REG
  2528                              <1>         ;add	dx, [NABMBAR]
  2529                              <1> 	;out	dx, al
  2530                              <1> 
  2531                              <1> 	; 10/10/2017
  2532                              <1> 	;jmp	short _ac97_ih3  ; exit
  2533 00012B06 C3                  <1> 	retn
  2534                              <1> 
  2535                              <1> ac97_stop: 
  2536                              <1> 	; 28/05/2017
  2537 00012B07 C605[34710100]00    <1> 	mov	byte [audio_play_cmd], 0 ; stop !
  2538                              <1> _ac97_stop: ; 09/10/2017
  2539                              <1> 	; 29/05/2017
  2540                              <1> 	;mov	dx, [NABMBAR]
  2541                              <1> 	;add	dx, PO_CR_REG
  2542                              <1> 	;mov	al, 0
  2543                              <1> 	;out	dx, al
  2544                              <1> 
  2545                              <1> 	; 11/06/2017
  2546 00012B0E 30C0                <1> 	xor	al, al ; 0
  2547 00012B10 E813000000          <1> 	call	ac97_po_cmd
  2548                              <1> 
  2549                              <1> 	; (Ref: KolibriOS, intelac97.asm, 'stop:')
  2550                              <1> 	; Clear FIFOE, BCIS, LVBCI (Ref: Intel ICH hub manual)
  2551 00012B15 66B81C00            <1> 	mov     ax, 1Ch
  2552 00012B19 668B15[3A710100]    <1> 	mov     dx, [NABMBAR]
  2553 00012B20 6683C216            <1> 	add     dx, PO_SR_REG
  2554 00012B24 66EF                <1> 	out     dx, ax
  2555                              <1> 
  2556                              <1> 	;retn
  2557                              <1> 
  2558                              <1> 	; 11/06/2017
  2559 00012B26 B002                <1> 	mov     al, RR
  2560                              <1> ac97_po_cmd:
  2561                              <1> 	 ;11/06/2017
  2562                              <1> 	; 29/05/2017
  2563 00012B28 668B15[3A710100]    <1> 	mov     dx, [NABMBAR]
  2564 00012B2F 6683C21B            <1>         add     dx, PO_CR_REG		; PCM out control register
  2565 00012B33 EE                  <1> 	out	dx, al
  2566 00012B34 C3                  <1> 	retn
  2567                              <1> 
  2568                              <1> ac97_pause:
  2569                              <1> 	; 11/06/2017
  2570                              <1> 	; 29/05/2017
  2571 00012B35 B010                <1> 	mov 	al, IOCE
  2572 00012B37 EBEF                <1> 	jmp	short ac97_po_cmd
  2573                              <1> 
  2574                              <1> reset_ac97_controller:
  2575                              <1> 	; 10/06/2017
  2576                              <1> 	; 29/05/2017
  2577                              <1> 	; 28/05/2017
  2578                              <1> 	; reset AC97 audio controller registers
  2579 00012B39 31C0                <1> 	xor     eax, eax
  2580 00012B3B 66BA0B00            <1>         mov	dx, PI_CR_REG
  2581 00012B3F 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2582 00012B46 EE                  <1> 	out     dx, al
  2583                              <1> 
  2584 00012B47 66BA1B00            <1>         mov     dx, PO_CR_REG
  2585 00012B4B 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2586 00012B52 EE                  <1> 	out     dx, al
  2587                              <1> 
  2588 00012B53 66BA2B00            <1>         mov     dx, MC_CR_REG
  2589 00012B57 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2590 00012B5E EE                  <1> 	out     dx, al
  2591                              <1> 
  2592 00012B5F B002                <1>         mov     al, RR
  2593 00012B61 66BA0B00            <1>         mov     dx, PI_CR_REG
  2594 00012B65 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2595 00012B6C EE                  <1> 	out     dx, al
  2596                              <1> 
  2597 00012B6D 66BA1B00            <1>         mov     dx, PO_CR_REG
  2598 00012B71 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2599 00012B78 EE                  <1> 	out     dx, al
  2600                              <1> 
  2601 00012B79 66BA2B00            <1>         mov     dx, MC_CR_REG
  2602 00012B7D 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2603 00012B84 EE                  <1> 	out     dx, al
  2604                              <1> 
  2605 00012B85 C3                  <1> 	retn
  2606                              <1> 
  2607                              <1> ac97_reset:
  2608                              <1> 	; 10/06/2017
  2609                              <1> 	; 29/05/2017
  2610                              <1> 	; 28/05/2017
  2611 00012B86 E8AEFFFFFF          <1> 	call	reset_ac97_controller
  2612                              <1> 	; 29/05/2017
  2613                              <1> 	;jmp	reset_ac97_codec
  2614                              <1> reset_ac97_codec:
  2615                              <1> 	; 28/05/2017 - Erdogan Tan (Ref: KolibriOS, intelac97.asm)
  2616 00012B8B 66BA2C00            <1> 	mov	dx, GLOB_CNT_REG ; 2Ch
  2617 00012B8F 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2618 00012B96 ED                  <1> 	in	eax, dx
  2619                              <1> 
  2620 00012B97 A902000000          <1> 	test	eax, 2
  2621 00012B9C 7407                <1> 	jz	short _r_ac97codec_cold	
  2622                              <1> 
  2623 00012B9E E80F000000          <1> 	call	warm_ac97codec_reset
  2624 00012BA3 7308                <1> 	jnc	short _r_ac97codec_ok
  2625                              <1> _r_ac97codec_cold:
  2626 00012BA5 E83D000000          <1>         call    cold_ac97codec_reset
  2627 00012BAA 7301                <1>         jnc     short _r_ac97codec_ok
  2628                              <1> 	
  2629                              <1> 	; 16/04/2017
  2630                              <1>         ;xor     eax, eax         ; timeout error
  2631                              <1>        	;stc
  2632 00012BAC C3                  <1> 	retn
  2633                              <1> 
  2634                              <1> _r_ac97codec_ok:
  2635 00012BAD 31C0                <1>         xor     eax, eax
  2636                              <1>         ;mov	al, VIA_ACLINK_C00_READY ; 1
  2637 00012BAF FEC0                <1>         inc	al
  2638 00012BB1 C3                  <1> 	retn
  2639                              <1> 
  2640                              <1> warm_ac97codec_reset:
  2641                              <1> 	; 28/05/2017 - Erdogan Tan (Ref: KolibriOS, intelac97.asm)
  2642 00012BB2 B806000000          <1>         mov     eax, 6
  2643 00012BB7 66BA2C00            <1> 	mov	dx, GLOB_CNT_REG ; 2Ch
  2644 00012BBB 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2645 00012BC2 EF                  <1> 	out	dx, eax
  2646                              <1> 
  2647 00012BC3 B90A000000          <1> 	mov	ecx, 10	; total 1s
  2648                              <1> _warm_ac97c_rst_wait:
  2649 00012BC8 51                  <1> 	push	ecx
  2650 00012BC9 E8ECF5FFFF          <1> 	call	delay_100ms
  2651 00012BCE 59                  <1> 	pop	ecx
  2652                              <1> 
  2653 00012BCF 66BA3000            <1> 	mov	dx, GLOB_STS_REG ; 30h
  2654 00012BD3 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2655 00012BDA ED                  <1> 	in	eax, dx
  2656                              <1> 
  2657 00012BDB A900030010          <1> 	test	eax, CTRL_ST_CREADY
  2658 00012BE0 7504                <1> 	jnz	short _warm_ac97c_rst_ok
  2659                              <1> 
  2660 00012BE2 49                  <1>         dec     ecx
  2661 00012BE3 75E3                <1>         jnz     short _warm_ac97c_rst_wait
  2662                              <1> 
  2663                              <1> _warm_ac97c_rst_fail:
  2664 00012BE5 F9                  <1>         stc
  2665                              <1> _warm_ac97c_rst_ok:
  2666 00012BE6 C3                  <1> 	retn
  2667                              <1> 
  2668                              <1> cold_ac97codec_reset:
  2669                              <1> 	; 28/05/2017 - Erdogan Tan (Ref: KolibriOS, intelac97.asm)
  2670 00012BE7 B802000000          <1>         mov     eax, 2
  2671 00012BEC 66BA2C00            <1> 	mov	dx, GLOB_CNT_REG ; 2Ch
  2672 00012BF0 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2673 00012BF7 EF                  <1> 	out	dx, eax
  2674                              <1> 
  2675 00012BF8 E8BDF5FFFF          <1> 	call	delay_100ms 	; wait 100 ms
  2676 00012BFD E8B8F5FFFF          <1> 	call	delay_100ms 	; wait 100 ms
  2677 00012C02 E8B3F5FFFF          <1> 	call	delay_100ms 	; wait 100 ms
  2678 00012C07 E8AEF5FFFF          <1> 	call	delay_100ms 	; wait 100 ms
  2679                              <1> 
  2680 00012C0C B910000000          <1> 	mov	ecx, 16	; total 20*100 ms = 2s
  2681                              <1> _cold_ac97c_rst_wait:
  2682 00012C11 66BA3000            <1> 	mov	dx, GLOB_STS_REG ; 30h
  2683 00012C15 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2684 00012C1C ED                  <1> 	in	eax, dx
  2685                              <1> 
  2686 00012C1D A900030010          <1> 	test	eax, CTRL_ST_CREADY
  2687 00012C22 750B                <1> 	jnz	short _cold_ac97c_rst_ok
  2688                              <1> 
  2689 00012C24 51                  <1> 	push	ecx
  2690 00012C25 E890F5FFFF          <1> 	call	delay_100ms
  2691 00012C2A 59                  <1> 	pop	ecx
  2692                              <1> 
  2693 00012C2B 49                  <1>         dec     ecx
  2694 00012C2C 75E3                <1>         jnz     short _cold_ac97c_rst_wait
  2695                              <1> 
  2696                              <1> _cold_ac97c_rst_fail:
  2697 00012C2E F9                  <1>         stc
  2698                              <1> _cold_ac97c_rst_ok:
  2699 00012C2F C3                  <1> 	retn
  2700                              <1> 
  2701                              <1> sb16_current_sound_data:
  2702                              <1> 	; 20/08/2017
  2703                              <1> 	; 24/06/2017
  2704                              <1> 	; 22/06/2017
  2705                              <1> 	; get current sound (PCM out) data for graphics
  2706                              <1> 	; (for Sound Blaster 16)
  2707                              <1> 	; ebx = Physical address (on page boundary)
  2708                              <1> 	; ecx = Byte count
  2709                              <1> 	; [audio_buff_size]
  2710                              <1> 
  2711                              <1> 	;;mov	edi, [audio_buff_size]
  2712                              <1> 	;mov	edi, [audio_dmabuff_size]
  2713                              <1> 	;mov	esi, [audio_dma_buff]
  2714 00012C30 39CF                <1> 	cmp	edi, ecx
  2715 00012C32 7302                <1> 	jnb	short sb16_gcd_0
  2716 00012C34 89F9                <1> 	mov	ecx, edi
  2717                              <1> sb16_gcd_0:
  2718                              <1> 	; 20/08/2017
  2719 00012C36 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16
  2720 00012C3D 750F                <1> 	jne	short sb16_gcd_1 ; 8 bit DMA channel
  2721 00012C3F E4C6                <1> 	in	al, 0C6h ; DMA channel 5 count register
  2722 00012C41 88C2                <1> 	mov	dl, al	
  2723 00012C43 E4C6                <1> 	in	al, 0C6h
  2724 00012C45 88C6                <1> 	mov     dh, al
  2725 00012C47 0FB7C2              <1> 	movzx	eax, dx
  2726 00012C4A D1E0                <1> 	shl	eax, 1 ; word count -> byte count
  2727 00012C4C EB4E                <1> 	jmp	short sb16_gcd_2	
  2728                              <1> sb16_gcd_1:
  2729 00012C4E E403                <1> 	in	al, 03h ; DMA channel 1 count register
  2730 00012C50 88C2                <1> 	mov	dl, al	
  2731 00012C52 E403                <1> 	in	al, 03h
  2732 00012C54 88C6                <1> 	mov     dh, al
  2733 00012C56 0FB7C2              <1> 	movzx	eax, dx
  2734 00012C59 EB41                <1> 	jmp	short sb16_gcd_2
  2735                              <1> ;sb16_gcd_2:	
  2736                              <1> ;	cmp	eax, ecx
  2737                              <1> ;	jnb	short sb16_gcd_3 
  2738                              <1> ;	; remain count < graphics bytes
  2739                              <1> ;	mov	eax, ecx ; fix remain count to data size
  2740                              <1> ;sb16_gcd_3:	
  2741                              <1> ;	sub	edi, eax
  2742                              <1> ;	jna	short sb16_gcd_4
  2743                              <1> ;	add	esi, edi ; dma buffer offset
  2744                              <1> ;sb16_gcd_4:
  2745                              <1> ;	mov	edi, ebx ; buffer address (for graphics) 
  2746                              <1> ;	mov	[u.r0], ecx
  2747                              <1> ;	rep	movsb
  2748                              <1> ;	retn
  2749                              <1> 
  2750                              <1> get_current_sound_data:
  2751                              <1> 	; 24/06/2017
  2752                              <1> 	; 22/06/2017
  2753                              <1> 	; get current sound (PCM out) data for graphics
  2754                              <1> 	;
  2755                              <1> 	; ebx = Physical address (on page boundary)
  2756                              <1> 	; ecx = Byte count
  2757                              <1> 	; [audio_buff_size]
  2758                              <1> 
  2759                              <1> 	;mov	edi, [audio_buff_size]
  2760 00012C5B 8B3D[24710100]      <1> 	mov	edi, [audio_dmabuff_size]
  2761 00012C61 8B35[20710100]      <1> 	mov	esi, [audio_dma_buff]
  2762 00012C67 803D[01710100]02    <1> 	cmp	byte [audio_device], 2
  2763 00012C6E 72C0                <1> 	jb	short sb16_current_sound_data ; = 1
  2764 00012C70 D1EF                <1> 	shr	edi, 1
  2765 00012C72 39CF                <1> 	cmp	edi, ecx
  2766 00012C74 7302                <1> 	jnb	short gcd_0
  2767 00012C76 89F9                <1> 	mov	ecx, edi
  2768                              <1> gcd_0:
  2769 00012C78 803D[01710100]03    <1> 	cmp	byte [audio_device], 3
  2770 00012C7F 7232                <1> 	jb	short ac97_current_sound_data ; = 2
  2771                              <1> 	; = 3
  2772                              <1> vt8233_current_sound_data:
  2773                              <1> 	; 22/06/2017
  2774                              <1> 	; 21/06/2017
  2775                              <1> 	; get current sound (PCM out) data for graphics
  2776                              <1> 	; (for VT 8233, VT 8237R)
  2777                              <1> 	; ebx = Physical address (on page boundary)
  2778                              <1> 	; ecx = Byte count
  2779                              <1> 	; [audio_buff_size]
  2780                              <1> 	
  2781                              <1> 	;;mov	edi, [audio_buff_size]
  2782                              <1> 	;mov	edi, [audio_dmabuff_size]
  2783                              <1> 	;mov	esi, [audio_dma_buff]
  2784                              <1> 	;shr	edi, 1
  2785                              <1> 	;cmp	edi, ecx
  2786                              <1> 	;jnb	short vt8233_gcd_1
  2787                              <1> 	;mov	ecx, edi
  2788                              <1> vt8233_gcd_1:
  2789 00012C81 BA0C000000          <1> 	mov	edx, VIA_REG_OFFSET_CURR_COUNT
  2790 00012C86 E88FF5FFFF          <1> 	call	ctrl_io_r32
  2791 00012C8B 89C2                <1> 	mov	edx, eax ; remain count (bits 23-0),
  2792                              <1> 			 ; SGD index (bits 31-24) 
  2793 00012C8D 81E200000001        <1> 	and	edx, 1000000h ; SGD index (0 = 1st half)
  2794 00012C93 7402                <1> 	jz	short vt8233_gcd_2
  2795                              <1> 	; the second half of DMA buffer
  2796 00012C95 01FE                <1> 	add	esi, edi 
  2797                              <1> vt8233_gcd_2:	
  2798 00012C97 25FFFFFF00          <1> 	and	eax, 0FFFFFFh ; bits 23-0
  2799                              <1> ac97_gcd_2:
  2800                              <1> sb16_gcd_2:
  2801 00012C9C 39C8                <1> 	cmp	eax, ecx
  2802 00012C9E 7302                <1> 	jnb	short vt8233_gcd_3 
  2803                              <1> 	; remain count < graphics bytes
  2804 00012CA0 89C8                <1> 	mov	eax, ecx ; fix remain count to data size
  2805                              <1> vt8233_gcd_3:
  2806 00012CA2 29C7                <1> 	sub	edi, eax
  2807 00012CA4 7602                <1> 	jna	short vt8233_gcd_4
  2808 00012CA6 01FE                <1> 	add	esi, edi ; dma buffer offset
  2809                              <1> vt8233_gcd_4:
  2810 00012CA8 89DF                <1> 	mov	edi, ebx ; buffer address (for graphics) 
  2811 00012CAA 890D[64030300]      <1> 	mov	[u.r0], ecx
  2812 00012CB0 F3A4                <1> 	rep	movsb
  2813                              <1> vt8233_gcd_5:
  2814 00012CB2 C3                  <1> 	retn
  2815                              <1> 
  2816                              <1> ac97_current_sound_data:
  2817                              <1> 	; 23/06/2017
  2818                              <1> 	; 22/06/2017
  2819                              <1> 	; get current sound (PCM out) data for graphics
  2820                              <1> 	; (for AC'97, ICH)
  2821                              <1> 	; ebx = Physical address (on page boundary)
  2822                              <1> 	; ecx = Byte count
  2823                              <1> 	; [audio_buff_size]
  2824                              <1> 	
  2825                              <1> 	;;mov	edi, [audio_buff_size]
  2826                              <1> 	;mov	edi, [audio_dmabuff_size]
  2827                              <1> 	;mov	esi, [audio_dma_buff]
  2828                              <1> 	;shr	edi, 1
  2829                              <1> 	;cmp	edi, ecx
  2830                              <1> 	;jnb	short ac97_gcd_0
  2831                              <1> 	;mov	ecx, edi
  2832                              <1> ac97_gcd_0:
  2833 00012CB3 66BA1400            <1> 	mov	dx, PO_CIV_REG ; Position In Current Buff Reg
  2834 00012CB7 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2835 00012CBE EC                  <1> 	in	al, dx ; current index value
  2836 00012CBF A801                <1> 	test	al, 1
  2837 00012CC1 7402                <1> 	jz	short ac97_gcd_1
  2838 00012CC3 01FE                <1> 	add	esi, edi
  2839                              <1> ac97_gcd_1:
  2840 00012CC5 31C0                <1> 	xor	eax, eax
  2841 00012CC7 66BA1800            <1> 	mov	dx, PO_PICB_REG ; Position In Current Buff Reg
  2842 00012CCB 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2843 00012CD2 66ED                <1> 	in	ax, dx ; remain dwords
  2844 00012CD4 C1E002              <1> 	shl	eax, 2 ; remain bytes ; 23/06/2017 
  2845 00012CD7 EBC3                <1> 	jmp	short ac97_gcd_2
  2846                              <1> ;	cmp	eax, ecx
  2847                              <1> ;	jnb	short ac97_gcd_2 
  2848                              <1> ;	; remain count < graphics bytes
  2849                              <1> ;	mov	eax, ecx ; fix remain count to data size
  2850                              <1> ;ac97_gcd_2:	
  2851                              <1> ;	sub	edi, eax
  2852                              <1> ;	jna	short ac97_gcd_3
  2853                              <1> ;	add	esi, edi ; dma buffer offset
  2854                              <1> ;ac97_gcd_3:
  2855                              <1> ;	mov	edi, ebx ; buffer address (for graphics) 
  2856                              <1> ;	mov	[u.r0], ecx
  2857                              <1> ;	rep	movsb
  2858                              <1> ;	retn
  2859                              <1> 
  2860                              <1> sb16_get_dma_buff_off:
  2861                              <1> 	; 28/10/2017
  2862                              <1> 	; 24/06/2017
  2863                              <1> 	; 22/06/2017
  2864                              <1> 	; get current (PCM OUT DMA buffer) pointer
  2865                              <1> 	; (for Sound Blaster 16)
  2866                              <1> 
  2867                              <1> 	;mov	ecx, [audio_dmabuff_size]
  2868                              <1> 	;xor	ebx, ebx
  2869                              <1> 	;shr	ecx, 1
  2870                              <1> sb16_gdmabo_0:
  2871                              <1> 	; 28/10/2017
  2872 00012CD9 803D[30710100]10    <1> 	cmp	byte [audio_bps], 16
  2873 00012CE0 750F                <1> 	jne	short sb16_gdmabo_1 ; 8 bit DMA channel
  2874                              <1> 	; 16 bit DMA channel
  2875 00012CE2 E4C6                <1> 	in	al, 0C6h ; DMA channel 5 count register
  2876 00012CE4 88C2                <1> 	mov	dl, al	
  2877 00012CE6 E4C6                <1> 	in	al, 0C6h
  2878 00012CE8 88C6                <1> 	mov     dh, al
  2879 00012CEA 0FB7C2              <1> 	movzx	eax, dx
  2880 00012CED D1E0                <1> 	shl	eax, 1 ; word count -> byte count
  2881 00012CEF EB3D                <1> 	jmp	short sb16_gdmabo_2	
  2882                              <1> sb16_gdmabo_1:
  2883 00012CF1 E403                <1> 	in	al, 03h ; DMA channel 1 count register
  2884 00012CF3 88C2                <1> 	mov	dl, al	
  2885 00012CF5 E403                <1> 	in	al, 03h
  2886 00012CF7 88C6                <1> 	mov     dh, al
  2887 00012CF9 0FB7C2              <1> 	movzx	eax, dx
  2888 00012CFC EB30                <1> 	jmp	short sb16_gdmabo_2
  2889                              <1> 
  2890                              <1> get_dma_buffer_offset:
  2891                              <1> 	; 24/06/2017
  2892                              <1> 	; 22/06/2017
  2893                              <1> 	; get current sound (PCM out) data for graphics
  2894                              <1> 	;
  2895                              <1> 	; ebx = Physical address (on page boundary)
  2896                              <1> 	; ecx = Byte count
  2897                              <1> 	; [audio_buff_size]
  2898                              <1> 
  2899 00012CFE 8B0D[24710100]      <1> 	mov	ecx, [audio_dmabuff_size]
  2900 00012D04 31DB                <1> 	xor	ebx, ebx
  2901                              <1> gdmabo_0:
  2902 00012D06 803D[01710100]02    <1> 	cmp	byte [audio_device], 2
  2903 00012D0D 72CA                <1> 	jb	short sb16_get_dma_buff_off
  2904 00012D0F 742A                <1> 	je	short ac97_get_dma_buff_off
  2905                              <1> 
  2906                              <1> vt8233_get_dma_buff_off:
  2907                              <1> 	; 24/06/2017
  2908                              <1> 	; 22/06/2017
  2909                              <1> 	; get current (PCM OUT DMA buffer) pointer
  2910                              <1> 	; (for VT 8233, VT 8237R)
  2911                              <1> 	
  2912                              <1> 	;mov	ecx, [audio_dmabuff_size]
  2913                              <1> 	;xor	ebx, ebx
  2914 00012D11 D1E9                <1> 	shr	ecx, 1
  2915                              <1> vt8233_gdmabo_0:
  2916 00012D13 BA0C000000          <1> 	mov	edx, VIA_REG_OFFSET_CURR_COUNT
  2917 00012D18 E8FDF4FFFF          <1> 	call	ctrl_io_r32
  2918 00012D1D 89C2                <1> 	mov	edx, eax ; remain count (bits 23-0),
  2919                              <1> 			 ; SGD index (bits 31-24) 
  2920 00012D1F 81E200000001        <1> 	and	edx, 1000000h ; SGD index (0 = 1st half)
  2921 00012D25 7402                <1> 	jz	short vt8233_gdmabo_1
  2922                              <1> 	; the second half of DMA buffer
  2923 00012D27 89CB                <1> 	mov	ebx, ecx 
  2924                              <1> vt8233_gdmabo_1:	
  2925 00012D29 25FFFFFF00          <1> 	and	eax, 0FFFFFFh ; bits 23-0
  2926                              <1> sb16_gdmabo_2:
  2927                              <1> ac97_gdmabo_2:
  2928 00012D2E 29C1                <1> 	sub	ecx, eax
  2929 00012D30 7602                <1> 	jna	short vt8233_gdmabo_2
  2930 00012D32 01CB                <1> 	add	ebx, ecx ; dma buffer offset
  2931                              <1> vt8233_gdmabo_2:
  2932 00012D34 891D[64030300]      <1> 	mov	[u.r0], ebx
  2933 00012D3A C3                  <1> 	retn
  2934                              <1> 
  2935                              <1> ac97_get_dma_buff_off:
  2936                              <1> 	; 24/06/2017
  2937                              <1> 	; 22/06/2017
  2938                              <1> 	; get current (PCM OUT DMA buffer) pointer
  2939                              <1> 	; (for AC'97, ICH)
  2940                              <1> 	; ebx = Physical address (on page boundary)
  2941                              <1> 	; ecx = Byte count
  2942                              <1> 	; [audio_buff_size]
  2943                              <1> 	
  2944                              <1> 	;mov	ecx, [audio_dmabuff_size]
  2945                              <1> 	;xor	ebx, ebx
  2946 00012D3B D1E9                <1> 	shr	ecx, 1
  2947                              <1> ac97_gdmabo_0:
  2948 00012D3D 66BA1400            <1> 	mov	dx, PO_CIV_REG ; Position In Current Buff Reg
  2949 00012D41 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2950 00012D48 EC                  <1> 	in	al, dx ; current index value
  2951 00012D49 A801                <1> 	test	al, 1
  2952 00012D4B 7402                <1> 	jz	short ac97_gdmabo_1
  2953 00012D4D 89CB                <1> 	mov	ebx, ecx
  2954                              <1> ac97_gdmabo_1:
  2955 00012D4F 31C0                <1> 	xor	eax, eax
  2956 00012D51 66BA1800            <1> 	mov	dx, PO_PICB_REG ; Position In Current Buff Reg
  2957 00012D55 660315[3A710100]    <1> 	add	dx, [NABMBAR]
  2958 00012D5C 66ED                <1> 	in	ax, dx ; remain dwords
  2959 00012D5E EBCE                <1> 	jmp	short ac97_gdmabo_2
  3198                                  
  3199                                  align 4
  3200                                  
  3201                                  %include 'vgadata.s' ; 04/07/2016
     1                              <1> ; ****************************************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.3 - vgadata.s  (palette and font data)
     3                              <1> ; -----------------------------------------------------------------------------
     4                              <1> ; Last Update: 25/11/2020
     5                              <1> ; -----------------------------------------------------------------------------
     6                              <1> ; Beginning: 16/01/2016
     7                              <1> ; -----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.15 (trdos386.s)
     9                              <1> ; -----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Plex86/Bochs VGABios' source code, vgabios-0.7a (2011)
    14                              <1> ; by the LGPL VGABios Developers Team (2001-2008), 'vgatables.h'
    15                              <1> ;
    16                              <1> ; Oracle VirtualBox 5.0.24 VGABios Source Code 
    17                              <1> ; ('vgabios.c', 'vgatables.h', 'vgafonts.h', 'vgarom.asm')
    18                              <1> ;
    19                              <1> ; Palette and font data in assembly language format:
    20                              <1> ; 'VBoxVgaBiosAlternative.asm'
    21                              <1> 
    22                              <1> ; ****************************************************************************************************
    23                              <1> 
    24                              <1> ; 25/11/2020 (TRDOS 386 v2.0.3)
    25                              <1> ; ('vgatables.h' - 30/12/2019 - vruppert)
    26                              <1>  
    27                              <1> ; 04/07/2016
    28                              <1> ; COLOR DATA
    29                              <1> 
    30                              <1> palette0: ; (63+1)*3
    31 00012D60 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
    31 00012D69 00000000000000      <1>
    32 00012D70 00000000000000002A- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    32 00012D79 2A2A2A2A2A2A2A      <1>
    33 00012D80 2A2A2A2A2A2A2A2A2A- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    33 00012D89 2A2A2A2A2A2A2A      <1>
    34 00012D90 2A2A2A2A2A2A2A2A2A- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    34 00012D99 2A2A2A2A2A2A2A      <1>
    35 00012DA0 2A2A2A2A2A2A2A2A3F- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh
    35 00012DA9 3F3F3F3F3F3F3F      <1>
    36 00012DB0 3F3F3F3F3F3F3F3F3F- <1>     db  03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh
    36 00012DB9 3F3F3F3F3F3F3F      <1>
    37 00012DC0 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
    37 00012DC9 00000000000000      <1>
    38 00012DD0 00000000000000002A- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    38 00012DD9 2A2A2A2A2A2A2A      <1>
    39 00012DE0 2A2A2A2A2A2A2A2A2A- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    39 00012DE9 2A2A2A2A2A2A2A      <1>
    40 00012DF0 2A2A2A2A2A2A2A2A2A- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah
    40 00012DF9 2A2A2A2A2A2A2A      <1>
    41 00012E00 2A2A2A2A2A2A2A2A3F- <1>     db  02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 02ah, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh
    41 00012E09 3F3F3F3F3F3F3F      <1>
    42 00012E10 3F3F3F3F3F3F3F3F3F- <1>     db  03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh, 03fh
    42 00012E19 3F3F3F3F3F3F3F      <1>
    43                              <1> palette1: ; (63+1)*3	
    44 00012E20 00000000002A002A00- <1>     db  000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah, 000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah
    44 00012E29 002A2A2A00002A      <1>
    45 00012E30 002A2A15002A2A2A00- <1>     db  000h, 02ah, 02ah, 015h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah
    45 00012E39 000000002A002A      <1>
    46 00012E40 00002A2A2A00002A00- <1>     db  000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah, 000h, 02ah, 02ah, 015h, 000h, 02ah, 02ah, 02ah
    46 00012E49 2A2A15002A2A2A      <1>
    47 00012E50 15151515153F153F15- <1>     db  015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh, 015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh
    47 00012E59 153F3F3F15153F      <1>
    48 00012E60 153F3F3F153F3F3F15- <1>     db  015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh
    48 00012E69 151515153F153F      <1>
    49 00012E70 15153F3F3F15153F15- <1>     db  015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh
    49 00012E79 3F3F3F153F3F3F      <1>
    50 00012E80 00000000002A002A00- <1>     db  000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah, 000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah
    50 00012E89 002A2A2A00002A      <1>
    51 00012E90 002A2A15002A2A2A00- <1>     db  000h, 02ah, 02ah, 015h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah
    51 00012E99 000000002A002A      <1>
    52 00012EA0 00002A2A2A00002A00- <1>     db  000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah, 000h, 02ah, 02ah, 015h, 000h, 02ah, 02ah, 02ah
    52 00012EA9 2A2A15002A2A2A      <1>
    53 00012EB0 15151515153F153F15- <1>     db  015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh, 015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh
    53 00012EB9 153F3F3F15153F      <1>
    54 00012EC0 153F3F3F153F3F3F15- <1>     db  015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh
    54 00012EC9 151515153F153F      <1>
    55 00012ED0 15153F3F3F15153F15- <1>     db  015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh
    55 00012ED9 3F3F3F153F3F3F      <1>
    56                              <1> palette2: ; (63+1)*3
    57 00012EE0 00000000002A002A00- <1>     db  000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah, 000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah
    57 00012EE9 002A2A2A00002A      <1>
    58 00012EF0 002A2A2A002A2A2A00- <1>     db  000h, 02ah, 02ah, 02ah, 000h, 02ah, 02ah, 02ah, 000h, 000h, 015h, 000h, 000h, 03fh, 000h, 02ah
    58 00012EF9 001500003F002A      <1>
    59 00012F00 15002A3F2A00152A00- <1>     db  015h, 000h, 02ah, 03fh, 02ah, 000h, 015h, 02ah, 000h, 03fh, 02ah, 02ah, 015h, 02ah, 02ah, 03fh
    59 00012F09 3F2A2A152A2A3F      <1>
    60 00012F10 00150000152A003F00- <1>     db  000h, 015h, 000h, 000h, 015h, 02ah, 000h, 03fh, 000h, 000h, 03fh, 02ah, 02ah, 015h, 000h, 02ah
    60 00012F19 003F2A2A15002A      <1>
    61 00012F20 152A2A3F002A3F2A00- <1>     db  015h, 02ah, 02ah, 03fh, 000h, 02ah, 03fh, 02ah, 000h, 015h, 015h, 000h, 015h, 03fh, 000h, 03fh
    61 00012F29 151500153F003F      <1>
    62 00012F30 15003F3F2A15152A15- <1>     db  015h, 000h, 03fh, 03fh, 02ah, 015h, 015h, 02ah, 015h, 03fh, 02ah, 03fh, 015h, 02ah, 03fh, 03fh
    62 00012F39 3F2A3F152A3F3F      <1>
    63 00012F40 15000015002A152A00- <1>     db  015h, 000h, 000h, 015h, 000h, 02ah, 015h, 02ah, 000h, 015h, 02ah, 02ah, 03fh, 000h, 000h, 03fh
    63 00012F49 152A2A3F00003F      <1>
    64 00012F50 002A3F2A003F2A2A15- <1>     db  000h, 02ah, 03fh, 02ah, 000h, 03fh, 02ah, 02ah, 015h, 000h, 015h, 015h, 000h, 03fh, 015h, 02ah
    64 00012F59 001515003F152A      <1>
    65 00012F60 15152A3F3F00153F00- <1>     db  015h, 015h, 02ah, 03fh, 03fh, 000h, 015h, 03fh, 000h, 03fh, 03fh, 02ah, 015h, 03fh, 02ah, 03fh
    65 00012F69 3F3F2A153F2A3F      <1>
    66 00012F70 15150015152A153F00- <1>     db  015h, 015h, 000h, 015h, 015h, 02ah, 015h, 03fh, 000h, 015h, 03fh, 02ah, 03fh, 015h, 000h, 03fh
    66 00012F79 153F2A3F15003F      <1>
    67 00012F80 152A3F3F003F3F2A15- <1>     db  015h, 02ah, 03fh, 03fh, 000h, 03fh, 03fh, 02ah, 015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh
    67 00012F89 151515153F153F      <1>
    68 00012F90 15153F3F3F15153F15- <1>     db  015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh
    68 00012F99 3F3F3F153F3F3F      <1>
    69                              <1> palette3: ; 256*3
    70 00012FA0 00000000002A002A00- <1>     db  000h, 000h, 000h, 000h, 000h, 02ah, 000h, 02ah, 000h, 000h, 02ah, 02ah, 02ah, 000h, 000h, 02ah
    70 00012FA9 002A2A2A00002A      <1>
    71 00012FB0 002A2A15002A2A2A15- <1>     db  000h, 02ah, 02ah, 015h, 000h, 02ah, 02ah, 02ah, 015h, 015h, 015h, 015h, 015h, 03fh, 015h, 03fh
    71 00012FB9 151515153F153F      <1>
    72 00012FC0 15153F3F3F15153F15- <1>     db  015h, 015h, 03fh, 03fh, 03fh, 015h, 015h, 03fh, 015h, 03fh, 03fh, 03fh, 015h, 03fh, 03fh, 03fh
    72 00012FC9 3F3F3F153F3F3F      <1>
    73 00012FD0 000000050505080808- <1>     db  000h, 000h, 000h, 005h, 005h, 005h, 008h, 008h, 008h, 00bh, 00bh, 00bh, 00eh, 00eh, 00eh, 011h
    73 00012FD9 0B0B0B0E0E0E11      <1>
    74 00012FE0 11111414141818181C- <1>     db  011h, 011h, 014h, 014h, 014h, 018h, 018h, 018h, 01ch, 01ch, 01ch, 020h, 020h, 020h, 024h, 024h
    74 00012FE9 1C1C2020202424      <1>
    75 00012FF0 242828282D2D2D3232- <1>     db  024h, 028h, 028h, 028h, 02dh, 02dh, 02dh, 032h, 032h, 032h, 038h, 038h, 038h, 03fh, 03fh, 03fh
    75 00012FF9 323838383F3F3F      <1>
    76 00013000 00003F10003F1F003F- <1>     db  000h, 000h, 03fh, 010h, 000h, 03fh, 01fh, 000h, 03fh, 02fh, 000h, 03fh, 03fh, 000h, 03fh, 03fh
    76 00013009 2F003F3F003F3F      <1>
    77 00013010 002F3F001F3F00103F- <1>     db  000h, 02fh, 03fh, 000h, 01fh, 03fh, 000h, 010h, 03fh, 000h, 000h, 03fh, 010h, 000h, 03fh, 01fh
    77 00013019 00003F10003F1F      <1>
    78 00013020 003F2F003F3F002F3F- <1>     db  000h, 03fh, 02fh, 000h, 03fh, 03fh, 000h, 02fh, 03fh, 000h, 01fh, 03fh, 000h, 010h, 03fh, 000h
    78 00013029 001F3F00103F00      <1>
    79 00013030 003F00003F10003F1F- <1>     db  000h, 03fh, 000h, 000h, 03fh, 010h, 000h, 03fh, 01fh, 000h, 03fh, 02fh, 000h, 03fh, 03fh, 000h
    79 00013039 003F2F003F3F00      <1>
    80 00013040 2F3F001F3F00103F1F- <1>     db  02fh, 03fh, 000h, 01fh, 03fh, 000h, 010h, 03fh, 01fh, 01fh, 03fh, 027h, 01fh, 03fh, 02fh, 01fh
    80 00013049 1F3F271F3F2F1F      <1>
    81 00013050 3F371F3F3F1F3F3F1F- <1>     db  03fh, 037h, 01fh, 03fh, 03fh, 01fh, 03fh, 03fh, 01fh, 037h, 03fh, 01fh, 02fh, 03fh, 01fh, 027h
    81 00013059 373F1F2F3F1F27      <1>
    82 00013060 3F1F1F3F271F3F2F1F- <1>     db  03fh, 01fh, 01fh, 03fh, 027h, 01fh, 03fh, 02fh, 01fh, 03fh, 037h, 01fh, 03fh, 03fh, 01fh, 037h
    82 00013069 3F371F3F3F1F37      <1>
    83 00013070 3F1F2F3F1F273F1F1F- <1>     db  03fh, 01fh, 02fh, 03fh, 01fh, 027h, 03fh, 01fh, 01fh, 03fh, 01fh, 01fh, 03fh, 027h, 01fh, 03fh
    83 00013079 3F1F1F3F271F3F      <1>
    84 00013080 2F1F3F371F3F3F1F37- <1>     db  02fh, 01fh, 03fh, 037h, 01fh, 03fh, 03fh, 01fh, 037h, 03fh, 01fh, 02fh, 03fh, 01fh, 027h, 03fh
    84 00013089 3F1F2F3F1F273F      <1>
    85 00013090 2D2D3F312D3F362D3F- <1>     db  02dh, 02dh, 03fh, 031h, 02dh, 03fh, 036h, 02dh, 03fh, 03ah, 02dh, 03fh, 03fh, 02dh, 03fh, 03fh
    85 00013099 3A2D3F3F2D3F3F      <1>
    86 000130A0 2D3A3F2D363F2D313F- <1>     db  02dh, 03ah, 03fh, 02dh, 036h, 03fh, 02dh, 031h, 03fh, 02dh, 02dh, 03fh, 031h, 02dh, 03fh, 036h
    86 000130A9 2D2D3F312D3F36      <1>
    87 000130B0 2D3F3A2D3F3F2D3A3F- <1>     db  02dh, 03fh, 03ah, 02dh, 03fh, 03fh, 02dh, 03ah, 03fh, 02dh, 036h, 03fh, 02dh, 031h, 03fh, 02dh
    87 000130B9 2D363F2D313F2D      <1>
    88 000130C0 2D3F2D2D3F312D3F36- <1>     db  02dh, 03fh, 02dh, 02dh, 03fh, 031h, 02dh, 03fh, 036h, 02dh, 03fh, 03ah, 02dh, 03fh, 03fh, 02dh
    88 000130C9 2D3F3A2D3F3F2D      <1>
    89 000130D0 3A3F2D363F2D313F00- <1>     db  03ah, 03fh, 02dh, 036h, 03fh, 02dh, 031h, 03fh, 000h, 000h, 01ch, 007h, 000h, 01ch, 00eh, 000h
    89 000130D9 001C07001C0E00      <1>
    90 000130E0 1C15001C1C001C1C00- <1>     db  01ch, 015h, 000h, 01ch, 01ch, 000h, 01ch, 01ch, 000h, 015h, 01ch, 000h, 00eh, 01ch, 000h, 007h
    90 000130E9 151C000E1C0007      <1>
    91 000130F0 1C00001C07001C0E00- <1>     db  01ch, 000h, 000h, 01ch, 007h, 000h, 01ch, 00eh, 000h, 01ch, 015h, 000h, 01ch, 01ch, 000h, 015h
    91 000130F9 1C15001C1C0015      <1>
    92 00013100 1C000E1C00071C0000- <1>     db  01ch, 000h, 00eh, 01ch, 000h, 007h, 01ch, 000h, 000h, 01ch, 000h, 000h, 01ch, 007h, 000h, 01ch
    92 00013109 1C00001C07001C      <1>
    93 00013110 0E001C15001C1C0015- <1>     db  00eh, 000h, 01ch, 015h, 000h, 01ch, 01ch, 000h, 015h, 01ch, 000h, 00eh, 01ch, 000h, 007h, 01ch
    93 00013119 1C000E1C00071C      <1>
    94 00013120 0E0E1C110E1C150E1C- <1>     db  00eh, 00eh, 01ch, 011h, 00eh, 01ch, 015h, 00eh, 01ch, 018h, 00eh, 01ch, 01ch, 00eh, 01ch, 01ch
    94 00013129 180E1C1C0E1C1C      <1>
    95 00013130 0E181C0E151C0E111C- <1>     db  00eh, 018h, 01ch, 00eh, 015h, 01ch, 00eh, 011h, 01ch, 00eh, 00eh, 01ch, 011h, 00eh, 01ch, 015h
    95 00013139 0E0E1C110E1C15      <1>
    96 00013140 0E1C180E1C1C0E181C- <1>     db  00eh, 01ch, 018h, 00eh, 01ch, 01ch, 00eh, 018h, 01ch, 00eh, 015h, 01ch, 00eh, 011h, 01ch, 00eh
    96 00013149 0E151C0E111C0E      <1>
    97 00013150 0E1C0E0E1C110E1C15- <1>     db  00eh, 01ch, 00eh, 00eh, 01ch, 011h, 00eh, 01ch, 015h, 00eh, 01ch, 018h, 00eh, 01ch, 01ch, 00eh
    97 00013159 0E1C180E1C1C0E      <1>
    98 00013160 181C0E151C0E111C14- <1>     db  018h, 01ch, 00eh, 015h, 01ch, 00eh, 011h, 01ch, 014h, 014h, 01ch, 016h, 014h, 01ch, 018h, 014h
    98 00013169 141C16141C1814      <1>
    99 00013170 1C1A141C1C141C1C14- <1>     db  01ch, 01ah, 014h, 01ch, 01ch, 014h, 01ch, 01ch, 014h, 01ah, 01ch, 014h, 018h, 01ch, 014h, 016h
    99 00013179 1A1C14181C1416      <1>
   100 00013180 1C14141C16141C1814- <1>     db  01ch, 014h, 014h, 01ch, 016h, 014h, 01ch, 018h, 014h, 01ch, 01ah, 014h, 01ch, 01ch, 014h, 01ah
   100 00013189 1C1A141C1C141A      <1>
   101 00013190 1C14181C14161C1414- <1>     db  01ch, 014h, 018h, 01ch, 014h, 016h, 01ch, 014h, 014h, 01ch, 014h, 014h, 01ch, 016h, 014h, 01ch
   101 00013199 1C14141C16141C      <1>
   102 000131A0 18141C1A141C1C141A- <1>     db  018h, 014h, 01ch, 01ah, 014h, 01ch, 01ch, 014h, 01ah, 01ch, 014h, 018h, 01ch, 014h, 016h, 01ch
   102 000131A9 1C14181C14161C      <1>
   103 000131B0 000010040010080010- <1>     db  000h, 000h, 010h, 004h, 000h, 010h, 008h, 000h, 010h, 00ch, 000h, 010h, 010h, 000h, 010h, 010h
   103 000131B9 0C001010001010      <1>
   104 000131C0 000C10000810000410- <1>     db  000h, 00ch, 010h, 000h, 008h, 010h, 000h, 004h, 010h, 000h, 000h, 010h, 004h, 000h, 010h, 008h
   104 000131C9 00001004001008      <1>
   105 000131D0 00100C001010000C10- <1>     db  000h, 010h, 00ch, 000h, 010h, 010h, 000h, 00ch, 010h, 000h, 008h, 010h, 000h, 004h, 010h, 000h
   105 000131D9 00081000041000      <1>
   106 000131E0 001000001004001008- <1>     db  000h, 010h, 000h, 000h, 010h, 004h, 000h, 010h, 008h, 000h, 010h, 00ch, 000h, 010h, 010h, 000h
   106 000131E9 00100C00101000      <1>
   107 000131F0 0C1000081000041008- <1>     db  00ch, 010h, 000h, 008h, 010h, 000h, 004h, 010h, 008h, 008h, 010h, 00ah, 008h, 010h, 00ch, 008h
   107 000131F9 08100A08100C08      <1>
   108 00013200 100E08101008101008- <1>     db  010h, 00eh, 008h, 010h, 010h, 008h, 010h, 010h, 008h, 00eh, 010h, 008h, 00ch, 010h, 008h, 00ah
   108 00013209 0E10080C10080A      <1>
   109 00013210 100808100A08100C08- <1>     db  010h, 008h, 008h, 010h, 00ah, 008h, 010h, 00ch, 008h, 010h, 00eh, 008h, 010h, 010h, 008h, 00eh
   109 00013219 100E081010080E      <1>
   110 00013220 10080C10080A100808- <1>     db  010h, 008h, 00ch, 010h, 008h, 00ah, 010h, 008h, 008h, 010h, 008h, 008h, 010h, 00ah, 008h, 010h
   110 00013229 100808100A0810      <1>
   111 00013230 0C08100E081010080E- <1>     db  00ch, 008h, 010h, 00eh, 008h, 010h, 010h, 008h, 00eh, 010h, 008h, 00ch, 010h, 008h, 00ah, 010h
   111 00013239 10080C10080A10      <1>
   112 00013240 0B0B100C0B100D0B10- <1>     db  00bh, 00bh, 010h, 00ch, 00bh, 010h, 00dh, 00bh, 010h, 00fh, 00bh, 010h, 010h, 00bh, 010h, 010h
   112 00013249 0F0B10100B1010      <1>
   113 00013250 0B0F100B0D100B0C10- <1>     db  00bh, 00fh, 010h, 00bh, 00dh, 010h, 00bh, 00ch, 010h, 00bh, 00bh, 010h, 00ch, 00bh, 010h, 00dh
   113 00013259 0B0B100C0B100D      <1>
   114 00013260 0B100F0B10100B0F10- <1>     db  00bh, 010h, 00fh, 00bh, 010h, 010h, 00bh, 00fh, 010h, 00bh, 00dh, 010h, 00bh, 00ch, 010h, 00bh
   114 00013269 0B0D100B0C100B      <1>
   115 00013270 0B100B0B100C0B100D- <1>     db  00bh, 010h, 00bh, 00bh, 010h, 00ch, 00bh, 010h, 00dh, 00bh, 010h, 00fh, 00bh, 010h, 010h, 00bh
   115 00013279 0B100F0B10100B      <1>
   116 00013280 0F100B0D100B0C1000- <1>     db  00fh, 010h, 00bh, 00dh, 010h, 00bh, 00ch, 010h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   116 00013289 00000000000000      <1>
   117 00013290 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   117 00013299 00000000000000      <1>
   118                              <1> 
   119                              <1> 
   120                              <1> ; 04/07/2016
   121                              <1> ; FONT DATA
   122                              <1> 
   123                              <1> CRT_CHAR_GEN:
   124                              <1> vgafont8: 
   125 000132A0 00000000000000007E- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07eh, 081h, 0a5h, 081h, 0bdh, 099h, 081h, 07eh
   125 000132A9 81A581BD99817E      <1>
   126 000132B0 7EFFDBFFC3E7FF7E6C- <1>     db  07eh, 0ffh, 0dbh, 0ffh, 0c3h, 0e7h, 0ffh, 07eh, 06ch, 0feh, 0feh, 0feh, 07ch, 038h, 010h, 000h
   126 000132B9 FEFEFE7C381000      <1>
   127 000132C0 10387CFE7C38100038- <1>     db  010h, 038h, 07ch, 0feh, 07ch, 038h, 010h, 000h, 038h, 07ch, 038h, 0feh, 0feh, 07ch, 038h, 07ch
   127 000132C9 7C38FEFE7C387C      <1>
   128 000132D0 1010387CFE7C387C00- <1>     db  010h, 010h, 038h, 07ch, 0feh, 07ch, 038h, 07ch, 000h, 000h, 018h, 03ch, 03ch, 018h, 000h, 000h
   128 000132D9 00183C3C180000      <1>
   129 000132E0 FFFFE7C3C3E7FFFF00- <1>     db  0ffh, 0ffh, 0e7h, 0c3h, 0c3h, 0e7h, 0ffh, 0ffh, 000h, 03ch, 066h, 042h, 042h, 066h, 03ch, 000h
   129 000132E9 3C664242663C00      <1>
   130 000132F0 FFC399BDBD99C3FF0F- <1>     db  0ffh, 0c3h, 099h, 0bdh, 0bdh, 099h, 0c3h, 0ffh, 00fh, 007h, 00fh, 07dh, 0cch, 0cch, 0cch, 078h
   130 000132F9 070F7DCCCCCC78      <1>
   131 00013300 3C6666663C187E183F- <1>     db  03ch, 066h, 066h, 066h, 03ch, 018h, 07eh, 018h, 03fh, 033h, 03fh, 030h, 030h, 070h, 0f0h, 0e0h
   131 00013309 333F303070F0E0      <1>
   132 00013310 7F637F636367E6C099- <1>     db  07fh, 063h, 07fh, 063h, 063h, 067h, 0e6h, 0c0h, 099h, 05ah, 03ch, 0e7h, 0e7h, 03ch, 05ah, 099h
   132 00013319 5A3CE7E73C5A99      <1>
   133 00013320 80E0F8FEF8E0800002- <1>     db  080h, 0e0h, 0f8h, 0feh, 0f8h, 0e0h, 080h, 000h, 002h, 00eh, 03eh, 0feh, 03eh, 00eh, 002h, 000h
   133 00013329 0E3EFE3E0E0200      <1>
   134 00013330 183C7E18187E3C1866- <1>     db  018h, 03ch, 07eh, 018h, 018h, 07eh, 03ch, 018h, 066h, 066h, 066h, 066h, 066h, 000h, 066h, 000h
   134 00013339 66666666006600      <1>
   135 00013340 7FDBDB7B1B1B1B003E- <1>     db  07fh, 0dbh, 0dbh, 07bh, 01bh, 01bh, 01bh, 000h, 03eh, 063h, 038h, 06ch, 06ch, 038h, 0cch, 078h
   135 00013349 63386C6C38CC78      <1>
   136 00013350 000000007E7E7E0018- <1>     db  000h, 000h, 000h, 000h, 07eh, 07eh, 07eh, 000h, 018h, 03ch, 07eh, 018h, 07eh, 03ch, 018h, 0ffh
   136 00013359 3C7E187E3C18FF      <1>
   137 00013360 183C7E181818180018- <1>     db  018h, 03ch, 07eh, 018h, 018h, 018h, 018h, 000h, 018h, 018h, 018h, 018h, 07eh, 03ch, 018h, 000h
   137 00013369 1818187E3C1800      <1>
   138 00013370 00180CFE0C18000000- <1>     db  000h, 018h, 00ch, 0feh, 00ch, 018h, 000h, 000h, 000h, 030h, 060h, 0feh, 060h, 030h, 000h, 000h
   138 00013379 3060FE60300000      <1>
   139 00013380 0000C0C0C0FE000000- <1>     db  000h, 000h, 0c0h, 0c0h, 0c0h, 0feh, 000h, 000h, 000h, 024h, 066h, 0ffh, 066h, 024h, 000h, 000h
   139 00013389 2466FF66240000      <1>
   140 00013390 00183C7EFFFF000000- <1>     db  000h, 018h, 03ch, 07eh, 0ffh, 0ffh, 000h, 000h, 000h, 0ffh, 0ffh, 07eh, 03ch, 018h, 000h, 000h
   140 00013399 FFFF7E3C180000      <1>
   141 000133A0 000000000000000030- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 030h, 078h, 078h, 030h, 030h, 000h, 030h, 000h
   141 000133A9 78783030003000      <1>
   142 000133B0 6C6C6C00000000006C- <1>     db  06ch, 06ch, 06ch, 000h, 000h, 000h, 000h, 000h, 06ch, 06ch, 0feh, 06ch, 0feh, 06ch, 06ch, 000h
   142 000133B9 6CFE6CFE6C6C00      <1>
   143 000133C0 307CC0780CF8300000- <1>     db  030h, 07ch, 0c0h, 078h, 00ch, 0f8h, 030h, 000h, 000h, 0c6h, 0cch, 018h, 030h, 066h, 0c6h, 000h
   143 000133C9 C6CC183066C600      <1>
   144 000133D0 386C3876DCCC760060- <1>     db  038h, 06ch, 038h, 076h, 0dch, 0cch, 076h, 000h, 060h, 060h, 0c0h, 000h, 000h, 000h, 000h, 000h
   144 000133D9 60C00000000000      <1>
   145 000133E0 183060606030180060- <1>     db  018h, 030h, 060h, 060h, 060h, 030h, 018h, 000h, 060h, 030h, 018h, 018h, 018h, 030h, 060h, 000h
   145 000133E9 30181818306000      <1>
   146 000133F0 00663CFF3C66000000- <1>     db  000h, 066h, 03ch, 0ffh, 03ch, 066h, 000h, 000h, 000h, 030h, 030h, 0fch, 030h, 030h, 000h, 000h
   146 000133F9 3030FC30300000      <1>
   147 00013400 000000000030306000- <1>     db  000h, 000h, 000h, 000h, 000h, 030h, 030h, 060h, 000h, 000h, 000h, 0fch, 000h, 000h, 000h, 000h
   147 00013409 0000FC00000000      <1>
   148 00013410 000000000030300006- <1>     db  000h, 000h, 000h, 000h, 000h, 030h, 030h, 000h, 006h, 00ch, 018h, 030h, 060h, 0c0h, 080h, 000h
   148 00013419 0C183060C08000      <1>
   149 00013420 7CC6CEDEF6E67C0030- <1>     db  07ch, 0c6h, 0ceh, 0deh, 0f6h, 0e6h, 07ch, 000h, 030h, 070h, 030h, 030h, 030h, 030h, 0fch, 000h
   149 00013429 7030303030FC00      <1>
   150 00013430 78CC0C3860CCFC0078- <1>     db  078h, 0cch, 00ch, 038h, 060h, 0cch, 0fch, 000h, 078h, 0cch, 00ch, 038h, 00ch, 0cch, 078h, 000h
   150 00013439 CC0C380CCC7800      <1>
   151 00013440 1C3C6CCCFE0C1E00FC- <1>     db  01ch, 03ch, 06ch, 0cch, 0feh, 00ch, 01eh, 000h, 0fch, 0c0h, 0f8h, 00ch, 00ch, 0cch, 078h, 000h
   151 00013449 C0F80C0CCC7800      <1>
   152 00013450 3860C0F8CCCC7800FC- <1>     db  038h, 060h, 0c0h, 0f8h, 0cch, 0cch, 078h, 000h, 0fch, 0cch, 00ch, 018h, 030h, 030h, 030h, 000h
   152 00013459 CC0C1830303000      <1>
   153 00013460 78CCCC78CCCC780078- <1>     db  078h, 0cch, 0cch, 078h, 0cch, 0cch, 078h, 000h, 078h, 0cch, 0cch, 07ch, 00ch, 018h, 070h, 000h
   153 00013469 CCCC7C0C187000      <1>
   154 00013470 003030000030300000- <1>     db  000h, 030h, 030h, 000h, 000h, 030h, 030h, 000h, 000h, 030h, 030h, 000h, 000h, 030h, 030h, 060h
   154 00013479 30300000303060      <1>
   155 00013480 183060C06030180000- <1>     db  018h, 030h, 060h, 0c0h, 060h, 030h, 018h, 000h, 000h, 000h, 0fch, 000h, 000h, 0fch, 000h, 000h
   155 00013489 00FC0000FC0000      <1>
   156 00013490 6030180C1830600078- <1>     db  060h, 030h, 018h, 00ch, 018h, 030h, 060h, 000h, 078h, 0cch, 00ch, 018h, 030h, 000h, 030h, 000h
   156 00013499 CC0C1830003000      <1>
   157 000134A0 7CC6DEDEDEC0780030- <1>     db  07ch, 0c6h, 0deh, 0deh, 0deh, 0c0h, 078h, 000h, 030h, 078h, 0cch, 0cch, 0fch, 0cch, 0cch, 000h
   157 000134A9 78CCCCFCCCCC00      <1>
   158 000134B0 FC66667C6666FC003C- <1>     db  0fch, 066h, 066h, 07ch, 066h, 066h, 0fch, 000h, 03ch, 066h, 0c0h, 0c0h, 0c0h, 066h, 03ch, 000h
   158 000134B9 66C0C0C0663C00      <1>
   159 000134C0 F86C6666666CF800FE- <1>     db  0f8h, 06ch, 066h, 066h, 066h, 06ch, 0f8h, 000h, 0feh, 062h, 068h, 078h, 068h, 062h, 0feh, 000h
   159 000134C9 6268786862FE00      <1>
   160 000134D0 FE6268786860F0003C- <1>     db  0feh, 062h, 068h, 078h, 068h, 060h, 0f0h, 000h, 03ch, 066h, 0c0h, 0c0h, 0ceh, 066h, 03eh, 000h
   160 000134D9 66C0C0CE663E00      <1>
   161 000134E0 CCCCCCFCCCCCCC0078- <1>     db  0cch, 0cch, 0cch, 0fch, 0cch, 0cch, 0cch, 000h, 078h, 030h, 030h, 030h, 030h, 030h, 078h, 000h
   161 000134E9 30303030307800      <1>
   162 000134F0 1E0C0C0CCCCC7800E6- <1>     db  01eh, 00ch, 00ch, 00ch, 0cch, 0cch, 078h, 000h, 0e6h, 066h, 06ch, 078h, 06ch, 066h, 0e6h, 000h
   162 000134F9 666C786C66E600      <1>
   163 00013500 F06060606266FE00C6- <1>     db  0f0h, 060h, 060h, 060h, 062h, 066h, 0feh, 000h, 0c6h, 0eeh, 0feh, 0feh, 0d6h, 0c6h, 0c6h, 000h
   163 00013509 EEFEFED6C6C600      <1>
   164 00013510 C6E6F6DECEC6C60038- <1>     db  0c6h, 0e6h, 0f6h, 0deh, 0ceh, 0c6h, 0c6h, 000h, 038h, 06ch, 0c6h, 0c6h, 0c6h, 06ch, 038h, 000h
   164 00013519 6CC6C6C66C3800      <1>
   165 00013520 FC66667C6060F00078- <1>     db  0fch, 066h, 066h, 07ch, 060h, 060h, 0f0h, 000h, 078h, 0cch, 0cch, 0cch, 0dch, 078h, 01ch, 000h
   165 00013529 CCCCCCDC781C00      <1>
   166 00013530 FC66667C6C66E60078- <1>     db  0fch, 066h, 066h, 07ch, 06ch, 066h, 0e6h, 000h, 078h, 0cch, 0e0h, 070h, 01ch, 0cch, 078h, 000h
   166 00013539 CCE0701CCC7800      <1>
   167 00013540 FCB4303030307800CC- <1>     db  0fch, 0b4h, 030h, 030h, 030h, 030h, 078h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 0fch, 000h
   167 00013549 CCCCCCCCCCFC00      <1>
   168 00013550 CCCCCCCCCC783000C6- <1>     db  0cch, 0cch, 0cch, 0cch, 0cch, 078h, 030h, 000h, 0c6h, 0c6h, 0c6h, 0d6h, 0feh, 0eeh, 0c6h, 000h
   168 00013559 C6C6D6FEEEC600      <1>
   169 00013560 C6C66C38386CC600CC- <1>     db  0c6h, 0c6h, 06ch, 038h, 038h, 06ch, 0c6h, 000h, 0cch, 0cch, 0cch, 078h, 030h, 030h, 078h, 000h
   169 00013569 CCCC7830307800      <1>
   170 00013570 FEC68C183266FE0078- <1>     db  0feh, 0c6h, 08ch, 018h, 032h, 066h, 0feh, 000h, 078h, 060h, 060h, 060h, 060h, 060h, 078h, 000h
   170 00013579 60606060607800      <1>
   171 00013580 C06030180C06020078- <1>     db  0c0h, 060h, 030h, 018h, 00ch, 006h, 002h, 000h, 078h, 018h, 018h, 018h, 018h, 018h, 078h, 000h
   171 00013589 18181818187800      <1>
   172 00013590 10386CC60000000000- <1>     db  010h, 038h, 06ch, 0c6h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh
   172 00013599 000000000000FF      <1>
   173 000135A0 303018000000000000- <1>     db  030h, 030h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 078h, 00ch, 07ch, 0cch, 076h, 000h
   173 000135A9 00780C7CCC7600      <1>
   174 000135B0 E060607C6666DC0000- <1>     db  0e0h, 060h, 060h, 07ch, 066h, 066h, 0dch, 000h, 000h, 000h, 078h, 0cch, 0c0h, 0cch, 078h, 000h
   174 000135B9 0078CCC0CC7800      <1>
   175 000135C0 1C0C0C7CCCCC760000- <1>     db  01ch, 00ch, 00ch, 07ch, 0cch, 0cch, 076h, 000h, 000h, 000h, 078h, 0cch, 0fch, 0c0h, 078h, 000h
   175 000135C9 0078CCFCC07800      <1>
   176 000135D0 386C60F06060F00000- <1>     db  038h, 06ch, 060h, 0f0h, 060h, 060h, 0f0h, 000h, 000h, 000h, 076h, 0cch, 0cch, 07ch, 00ch, 0f8h
   176 000135D9 0076CCCC7C0CF8      <1>
   177 000135E0 E0606C766666E60030- <1>     db  0e0h, 060h, 06ch, 076h, 066h, 066h, 0e6h, 000h, 030h, 000h, 070h, 030h, 030h, 030h, 078h, 000h
   177 000135E9 00703030307800      <1>
   178 000135F0 0C000C0C0CCCCC78E0- <1>     db  00ch, 000h, 00ch, 00ch, 00ch, 0cch, 0cch, 078h, 0e0h, 060h, 066h, 06ch, 078h, 06ch, 0e6h, 000h
   178 000135F9 60666C786CE600      <1>
   179 00013600 703030303030780000- <1>     db  070h, 030h, 030h, 030h, 030h, 030h, 078h, 000h, 000h, 000h, 0cch, 0feh, 0feh, 0d6h, 0c6h, 000h
   179 00013609 00CCFEFED6C600      <1>
   180 00013610 0000F8CCCCCCCC0000- <1>     db  000h, 000h, 0f8h, 0cch, 0cch, 0cch, 0cch, 000h, 000h, 000h, 078h, 0cch, 0cch, 0cch, 078h, 000h
   180 00013619 0078CCCCCC7800      <1>
   181 00013620 0000DC66667C60F000- <1>     db  000h, 000h, 0dch, 066h, 066h, 07ch, 060h, 0f0h, 000h, 000h, 076h, 0cch, 0cch, 07ch, 00ch, 01eh
   181 00013629 0076CCCC7C0C1E      <1>
   182 00013630 0000DC766660F00000- <1>     db  000h, 000h, 0dch, 076h, 066h, 060h, 0f0h, 000h, 000h, 000h, 07ch, 0c0h, 078h, 00ch, 0f8h, 000h
   182 00013639 007CC0780CF800      <1>
   183 00013640 10307C303034180000- <1>     db  010h, 030h, 07ch, 030h, 030h, 034h, 018h, 000h, 000h, 000h, 0cch, 0cch, 0cch, 0cch, 076h, 000h
   183 00013649 00CCCCCCCC7600      <1>
   184 00013650 0000CCCCCC78300000- <1>     db  000h, 000h, 0cch, 0cch, 0cch, 078h, 030h, 000h, 000h, 000h, 0c6h, 0d6h, 0feh, 0feh, 06ch, 000h
   184 00013659 00C6D6FEFE6C00      <1>
   185 00013660 0000C66C386CC60000- <1>     db  000h, 000h, 0c6h, 06ch, 038h, 06ch, 0c6h, 000h, 000h, 000h, 0cch, 0cch, 0cch, 07ch, 00ch, 0f8h
   185 00013669 00CCCCCC7C0CF8      <1>
   186 00013670 0000FC983064FC001C- <1>     db  000h, 000h, 0fch, 098h, 030h, 064h, 0fch, 000h, 01ch, 030h, 030h, 0e0h, 030h, 030h, 01ch, 000h
   186 00013679 3030E030301C00      <1>
   187 00013680 1818180018181800E0- <1>     db  018h, 018h, 018h, 000h, 018h, 018h, 018h, 000h, 0e0h, 030h, 030h, 01ch, 030h, 030h, 0e0h, 000h
   187 00013689 30301C3030E000      <1>
   188 00013690 76DC00000000000000- <1>     db  076h, 0dch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 000h
   188 00013699 10386CC6C6FE00      <1>
   189 000136A0 78CCC0CC78180C7800- <1>     db  078h, 0cch, 0c0h, 0cch, 078h, 018h, 00ch, 078h, 000h, 0cch, 000h, 0cch, 0cch, 0cch, 07eh, 000h
   189 000136A9 CC00CCCCCC7E00      <1>
   190 000136B0 1C0078CCFCC078007E- <1>     db  01ch, 000h, 078h, 0cch, 0fch, 0c0h, 078h, 000h, 07eh, 0c3h, 03ch, 006h, 03eh, 066h, 03fh, 000h
   190 000136B9 C33C063E663F00      <1>
   191 000136C0 CC00780C7CCC7E00E0- <1>     db  0cch, 000h, 078h, 00ch, 07ch, 0cch, 07eh, 000h, 0e0h, 000h, 078h, 00ch, 07ch, 0cch, 07eh, 000h
   191 000136C9 00780C7CCC7E00      <1>
   192 000136D0 3030780C7CCC7E0000- <1>     db  030h, 030h, 078h, 00ch, 07ch, 0cch, 07eh, 000h, 000h, 000h, 078h, 0c0h, 0c0h, 078h, 00ch, 038h
   192 000136D9 0078C0C0780C38      <1>
   193 000136E0 7EC33C667E603C00CC- <1>     db  07eh, 0c3h, 03ch, 066h, 07eh, 060h, 03ch, 000h, 0cch, 000h, 078h, 0cch, 0fch, 0c0h, 078h, 000h
   193 000136E9 0078CCFCC07800      <1>
   194 000136F0 E00078CCFCC07800CC- <1>     db  0e0h, 000h, 078h, 0cch, 0fch, 0c0h, 078h, 000h, 0cch, 000h, 070h, 030h, 030h, 030h, 078h, 000h
   194 000136F9 00703030307800      <1>
   195 00013700 7CC6381818183C00E0- <1>     db  07ch, 0c6h, 038h, 018h, 018h, 018h, 03ch, 000h, 0e0h, 000h, 070h, 030h, 030h, 030h, 078h, 000h
   195 00013709 00703030307800      <1>
   196 00013710 C6386CC6FEC6C60030- <1>     db  0c6h, 038h, 06ch, 0c6h, 0feh, 0c6h, 0c6h, 000h, 030h, 030h, 000h, 078h, 0cch, 0fch, 0cch, 000h
   196 00013719 300078CCFCCC00      <1>
   197 00013720 1C00FC607860FC0000- <1>     db  01ch, 000h, 0fch, 060h, 078h, 060h, 0fch, 000h, 000h, 000h, 07fh, 00ch, 07fh, 0cch, 07fh, 000h
   197 00013729 007F0C7FCC7F00      <1>
   198 00013730 3E6CCCFECCCCCE0078- <1>     db  03eh, 06ch, 0cch, 0feh, 0cch, 0cch, 0ceh, 000h, 078h, 0cch, 000h, 078h, 0cch, 0cch, 078h, 000h
   198 00013739 CC0078CCCC7800      <1>
   199 00013740 00CC0078CCCC780000- <1>     db  000h, 0cch, 000h, 078h, 0cch, 0cch, 078h, 000h, 000h, 0e0h, 000h, 078h, 0cch, 0cch, 078h, 000h
   199 00013749 E00078CCCC7800      <1>
   200 00013750 78CC00CCCCCC7E0000- <1>     db  078h, 0cch, 000h, 0cch, 0cch, 0cch, 07eh, 000h, 000h, 0e0h, 000h, 0cch, 0cch, 0cch, 07eh, 000h
   200 00013759 E000CCCCCC7E00      <1>
   201 00013760 00CC00CCCC7C0CF8C3- <1>     db  000h, 0cch, 000h, 0cch, 0cch, 07ch, 00ch, 0f8h, 0c3h, 018h, 03ch, 066h, 066h, 03ch, 018h, 000h
   201 00013769 183C66663C1800      <1>
   202 00013770 CC00CCCCCCCC780018- <1>     db  0cch, 000h, 0cch, 0cch, 0cch, 0cch, 078h, 000h, 018h, 018h, 07eh, 0c0h, 0c0h, 07eh, 018h, 018h
   202 00013779 187EC0C07E1818      <1>
   203 00013780 386C64F060E6FC00CC- <1>     db  038h, 06ch, 064h, 0f0h, 060h, 0e6h, 0fch, 000h, 0cch, 0cch, 078h, 0fch, 030h, 0fch, 030h, 030h
   203 00013789 CC78FC30FC3030      <1>
   204 00013790 F8CCCCFAC6CFC6C70E- <1>     db  0f8h, 0cch, 0cch, 0fah, 0c6h, 0cfh, 0c6h, 0c7h, 00eh, 01bh, 018h, 03ch, 018h, 018h, 0d8h, 070h
   204 00013799 1B183C1818D870      <1>
   205 000137A0 1C00780C7CCC7E0038- <1>     db  01ch, 000h, 078h, 00ch, 07ch, 0cch, 07eh, 000h, 038h, 000h, 070h, 030h, 030h, 030h, 078h, 000h
   205 000137A9 00703030307800      <1>
   206 000137B0 001C0078CCCC780000- <1>     db  000h, 01ch, 000h, 078h, 0cch, 0cch, 078h, 000h, 000h, 01ch, 000h, 0cch, 0cch, 0cch, 07eh, 000h
   206 000137B9 1C00CCCCCC7E00      <1>
   207 000137C0 00F800F8CCCCCC00FC- <1>     db  000h, 0f8h, 000h, 0f8h, 0cch, 0cch, 0cch, 000h, 0fch, 000h, 0cch, 0ech, 0fch, 0dch, 0cch, 000h
   207 000137C9 00CCECFCDCCC00      <1>
   208 000137D0 3C6C6C3E007E000038- <1>     db  03ch, 06ch, 06ch, 03eh, 000h, 07eh, 000h, 000h, 038h, 06ch, 06ch, 038h, 000h, 07ch, 000h, 000h
   208 000137D9 6C6C38007C0000      <1>
   209 000137E0 30003060C0CC780000- <1>     db  030h, 000h, 030h, 060h, 0c0h, 0cch, 078h, 000h, 000h, 000h, 000h, 0fch, 0c0h, 0c0h, 000h, 000h
   209 000137E9 0000FCC0C00000      <1>
   210 000137F0 000000FC0C0C0000C3- <1>     db  000h, 000h, 000h, 0fch, 00ch, 00ch, 000h, 000h, 0c3h, 0c6h, 0cch, 0deh, 033h, 066h, 0cch, 00fh
   210 000137F9 C6CCDE3366CC0F      <1>
   211 00013800 C3C6CCDB376FCF0318- <1>     db  0c3h, 0c6h, 0cch, 0dbh, 037h, 06fh, 0cfh, 003h, 018h, 018h, 000h, 018h, 018h, 018h, 018h, 000h
   211 00013809 18001818181800      <1>
   212 00013810 003366CC6633000000- <1>     db  000h, 033h, 066h, 0cch, 066h, 033h, 000h, 000h, 000h, 0cch, 066h, 033h, 066h, 0cch, 000h, 000h
   212 00013819 CC663366CC0000      <1>
   213 00013820 228822882288228855- <1>     db  022h, 088h, 022h, 088h, 022h, 088h, 022h, 088h, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah
   213 00013829 AA55AA55AA55AA      <1>
   214 00013830 DB77DBEEDB77DBEE18- <1>     db  0dbh, 077h, 0dbh, 0eeh, 0dbh, 077h, 0dbh, 0eeh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   214 00013839 18181818181818      <1>
   215 00013840 18181818F818181818- <1>     db  018h, 018h, 018h, 018h, 0f8h, 018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 0f8h, 018h, 018h, 018h
   215 00013849 18F818F8181818      <1>
   216 00013850 36363636F636363600- <1>     db  036h, 036h, 036h, 036h, 0f6h, 036h, 036h, 036h, 000h, 000h, 000h, 000h, 0feh, 036h, 036h, 036h
   216 00013859 000000FE363636      <1>
   217 00013860 0000F818F818181836- <1>     db  000h, 000h, 0f8h, 018h, 0f8h, 018h, 018h, 018h, 036h, 036h, 0f6h, 006h, 0f6h, 036h, 036h, 036h
   217 00013869 36F606F6363636      <1>
   218 00013870 363636363636363600- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 000h, 000h, 0feh, 006h, 0f6h, 036h, 036h, 036h
   218 00013879 00FE06F6363636      <1>
   219 00013880 3636F606FE00000036- <1>     db  036h, 036h, 0f6h, 006h, 0feh, 000h, 000h, 000h, 036h, 036h, 036h, 036h, 0feh, 000h, 000h, 000h
   219 00013889 363636FE000000      <1>
   220 00013890 1818F818F800000000- <1>     db  018h, 018h, 0f8h, 018h, 0f8h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0f8h, 018h, 018h, 018h
   220 00013899 000000F8181818      <1>
   221 000138A0 181818181F00000018- <1>     db  018h, 018h, 018h, 018h, 01fh, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 0ffh, 000h, 000h, 000h
   221 000138A9 181818FF000000      <1>
   222 000138B0 00000000FF18181818- <1>     db  000h, 000h, 000h, 000h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 01fh, 018h, 018h, 018h
   222 000138B9 1818181F181818      <1>
   223 000138C0 00000000FF00000018- <1>     db  000h, 000h, 000h, 000h, 0ffh, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 0ffh, 018h, 018h, 018h
   223 000138C9 181818FF181818      <1>
   224 000138D0 18181F181F18181836- <1>     db  018h, 018h, 01fh, 018h, 01fh, 018h, 018h, 018h, 036h, 036h, 036h, 036h, 037h, 036h, 036h, 036h
   224 000138D9 36363637363636      <1>
   225 000138E0 363637303F00000000- <1>     db  036h, 036h, 037h, 030h, 03fh, 000h, 000h, 000h, 000h, 000h, 03fh, 030h, 037h, 036h, 036h, 036h
   225 000138E9 003F3037363636      <1>
   226 000138F0 3636F700FF00000000- <1>     db  036h, 036h, 0f7h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0f7h, 036h, 036h, 036h
   226 000138F9 00FF00F7363636      <1>
   227 00013900 363637303736363600- <1>     db  036h, 036h, 037h, 030h, 037h, 036h, 036h, 036h, 000h, 000h, 0ffh, 000h, 0ffh, 000h, 000h, 000h
   227 00013909 00FF00FF000000      <1>
   228 00013910 3636F700F736363618- <1>     db  036h, 036h, 0f7h, 000h, 0f7h, 036h, 036h, 036h, 018h, 018h, 0ffh, 000h, 0ffh, 000h, 000h, 000h
   228 00013919 18FF00FF000000      <1>
   229 00013920 36363636FF00000000- <1>     db  036h, 036h, 036h, 036h, 0ffh, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0ffh, 018h, 018h, 018h
   229 00013929 00FF00FF181818      <1>
   230 00013930 00000000FF36363636- <1>     db  000h, 000h, 000h, 000h, 0ffh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 03fh, 000h, 000h, 000h
   230 00013939 3636363F000000      <1>
   231 00013940 18181F181F00000000- <1>     db  018h, 018h, 01fh, 018h, 01fh, 000h, 000h, 000h, 000h, 000h, 01fh, 018h, 01fh, 018h, 018h, 018h
   231 00013949 001F181F181818      <1>
   232 00013950 000000003F36363636- <1>     db  000h, 000h, 000h, 000h, 03fh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 0ffh, 036h, 036h, 036h
   232 00013959 363636FF363636      <1>
   233 00013960 1818FF18FF18181818- <1>     db  018h, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0f8h, 000h, 000h, 000h
   233 00013969 181818F8000000      <1>
   234 00013970 000000001F181818FF- <1>     db  000h, 000h, 000h, 000h, 01fh, 018h, 018h, 018h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   234 00013979 FFFFFFFFFFFFFF      <1>
   235 00013980 00000000FFFFFFFFF0- <1>     db  000h, 000h, 000h, 000h, 0ffh, 0ffh, 0ffh, 0ffh, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h
   235 00013989 F0F0F0F0F0F0F0      <1>
   236 00013990 0F0F0F0F0F0F0F0FFF- <1>     db  00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h, 000h, 000h
   236 00013999 FFFFFF00000000      <1>
   237 000139A0 000076DCC8DC760000- <1>     db  000h, 000h, 076h, 0dch, 0c8h, 0dch, 076h, 000h, 000h, 078h, 0cch, 0f8h, 0cch, 0f8h, 0c0h, 0c0h
   237 000139A9 78CCF8CCF8C0C0      <1>
   238 000139B0 00FCCCC0C0C0C00000- <1>     db  000h, 0fch, 0cch, 0c0h, 0c0h, 0c0h, 0c0h, 000h, 000h, 0feh, 06ch, 06ch, 06ch, 06ch, 06ch, 000h
   238 000139B9 FE6C6C6C6C6C00      <1>
   239 000139C0 FCCC603060CCFC0000- <1>     db  0fch, 0cch, 060h, 030h, 060h, 0cch, 0fch, 000h, 000h, 000h, 07eh, 0d8h, 0d8h, 0d8h, 070h, 000h
   239 000139C9 007ED8D8D87000      <1>
   240 000139D0 00666666667C60C000- <1>     db  000h, 066h, 066h, 066h, 066h, 07ch, 060h, 0c0h, 000h, 076h, 0dch, 018h, 018h, 018h, 018h, 000h
   240 000139D9 76DC1818181800      <1>
   241 000139E0 FC3078CCCC7830FC38- <1>     db  0fch, 030h, 078h, 0cch, 0cch, 078h, 030h, 0fch, 038h, 06ch, 0c6h, 0feh, 0c6h, 06ch, 038h, 000h
   241 000139E9 6CC6FEC66C3800      <1>
   242 000139F0 386CC6C66C6CEE001C- <1>     db  038h, 06ch, 0c6h, 0c6h, 06ch, 06ch, 0eeh, 000h, 01ch, 030h, 018h, 07ch, 0cch, 0cch, 078h, 000h
   242 000139F9 30187CCCCC7800      <1>
   243 00013A00 00007EDBDB7E000006- <1>     db  000h, 000h, 07eh, 0dbh, 0dbh, 07eh, 000h, 000h, 006h, 00ch, 07eh, 0dbh, 0dbh, 07eh, 060h, 0c0h
   243 00013A09 0C7EDBDB7E60C0      <1>
   244 00013A10 3860C0F8C060380078- <1>     db  038h, 060h, 0c0h, 0f8h, 0c0h, 060h, 038h, 000h, 078h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 000h
   244 00013A19 CCCCCCCCCCCC00      <1>
   245 00013A20 00FC00FC00FC000030- <1>     db  000h, 0fch, 000h, 0fch, 000h, 0fch, 000h, 000h, 030h, 030h, 0fch, 030h, 030h, 000h, 0fch, 000h
   245 00013A29 30FC303000FC00      <1>
   246 00013A30 603018306000FC0018- <1>     db  060h, 030h, 018h, 030h, 060h, 000h, 0fch, 000h, 018h, 030h, 060h, 030h, 018h, 000h, 0fch, 000h
   246 00013A39 3060301800FC00      <1>
   247 00013A40 0E1B1B181818181818- <1>     db  00eh, 01bh, 01bh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0d8h, 0d8h, 070h
   247 00013A49 18181818D8D870      <1>
   248 00013A50 303000FC0030300000- <1>     db  030h, 030h, 000h, 0fch, 000h, 030h, 030h, 000h, 000h, 076h, 0dch, 000h, 076h, 0dch, 000h, 000h
   248 00013A59 76DC0076DC0000      <1>
   249 00013A60 386C6C380000000000- <1>     db  038h, 06ch, 06ch, 038h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h
   249 00013A69 00001818000000      <1>
   250 00013A70 00000000180000000F- <1>     db  000h, 000h, 000h, 000h, 018h, 000h, 000h, 000h, 00fh, 00ch, 00ch, 00ch, 0ech, 06ch, 03ch, 01ch
   250 00013A79 0C0C0CEC6C3C1C      <1>
   251 00013A80 786C6C6C6C00000070- <1>     db  078h, 06ch, 06ch, 06ch, 06ch, 000h, 000h, 000h, 070h, 018h, 030h, 060h, 078h, 000h, 000h, 000h
   251 00013A89 18306078000000      <1>
   252 00013A90 00003C3C3C3C000000- <1>     db  000h, 000h, 03ch, 03ch, 03ch, 03ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   252 00013A99 00000000000000      <1>
   253                              <1> vgafont14:
   254 00013AA0 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   254 00013AA9 00000000000000      <1>
   255 00013AB0 7E81A58181BD99817E- <1>     db  07eh, 081h, 0a5h, 081h, 081h, 0bdh, 099h, 081h, 07eh, 000h, 000h, 000h, 000h, 000h, 07eh, 0ffh
   255 00013AB9 00000000007EFF      <1>
   256 00013AC0 DBFFFFC3E7FF7E0000- <1>     db  0dbh, 0ffh, 0ffh, 0c3h, 0e7h, 0ffh, 07eh, 000h, 000h, 000h, 000h, 000h, 000h, 06ch, 0feh, 0feh
   256 00013AC9 000000006CFEFE      <1>
   257 00013AD0 FEFE7C381000000000- <1>     db  0feh, 0feh, 07ch, 038h, 010h, 000h, 000h, 000h, 000h, 000h, 000h, 010h, 038h, 07ch, 0feh, 07ch
   257 00013AD9 000010387CFE7C      <1>
   258 00013AE0 381000000000000018- <1>     db  038h, 010h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 03ch, 03ch, 0e7h, 0e7h, 0e7h, 018h, 018h
   258 00013AE9 3C3CE7E7E71818      <1>
   259 00013AF0 3C0000000000183C7E- <1>     db  03ch, 000h, 000h, 000h, 000h, 000h, 018h, 03ch, 07eh, 0ffh, 0ffh, 07eh, 018h, 018h, 03ch, 000h
   259 00013AF9 FFFF7E18183C00      <1>
   260 00013B00 00000000000000183C- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 03ch, 03ch, 018h, 000h, 000h, 000h, 000h, 000h
   260 00013B09 3C180000000000      <1>
   261 00013B10 FFFFFFFFFFE7C3C3E7- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0e7h, 0c3h, 0c3h, 0e7h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h
   261 00013B19 FFFFFFFFFF0000      <1>
   262 00013B20 00003C664242663C00- <1>     db  000h, 000h, 03ch, 066h, 042h, 042h, 066h, 03ch, 000h, 000h, 000h, 000h, 0ffh, 0ffh, 0ffh, 0ffh
   262 00013B29 000000FFFFFFFF      <1>
   263 00013B30 C399BDBD99C3FFFFFF- <1>     db  0c3h, 099h, 0bdh, 0bdh, 099h, 0c3h, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h, 01eh, 00eh, 01ah, 032h
   263 00013B39 FF00001E0E1A32      <1>
   264 00013B40 78CCCCCC7800000000- <1>     db  078h, 0cch, 0cch, 0cch, 078h, 000h, 000h, 000h, 000h, 000h, 03ch, 066h, 066h, 066h, 03ch, 018h
   264 00013B49 003C6666663C18      <1>
   265 00013B50 7E181800000000003F- <1>     db  07eh, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 03fh, 033h, 03fh, 030h, 030h, 030h, 070h, 0f0h
   265 00013B59 333F30303070F0      <1>
   266 00013B60 E000000000007F637F- <1>     db  0e0h, 000h, 000h, 000h, 000h, 000h, 07fh, 063h, 07fh, 063h, 063h, 063h, 067h, 0e7h, 0e6h, 0c0h
   266 00013B69 63636367E7E6C0      <1>
   267 00013B70 000000001818DB3CE7- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 0dbh, 03ch, 0e7h, 03ch, 0dbh, 018h, 018h, 000h, 000h, 000h
   267 00013B79 3CDB1818000000      <1>
   268 00013B80 000080C0E0F8FEF8E0- <1>     db  000h, 000h, 080h, 0c0h, 0e0h, 0f8h, 0feh, 0f8h, 0e0h, 0c0h, 080h, 000h, 000h, 000h, 000h, 000h
   268 00013B89 C0800000000000      <1>
   269 00013B90 02060E3EFE3E0E0602- <1>     db  002h, 006h, 00eh, 03eh, 0feh, 03eh, 00eh, 006h, 002h, 000h, 000h, 000h, 000h, 000h, 018h, 03ch
   269 00013B99 0000000000183C      <1>
   270 00013BA0 7E1818187E3C180000- <1>     db  07eh, 018h, 018h, 018h, 07eh, 03ch, 018h, 000h, 000h, 000h, 000h, 000h, 066h, 066h, 066h, 066h
   270 00013BA9 00000066666666      <1>
   271 00013BB0 666600666600000000- <1>     db  066h, 066h, 000h, 066h, 066h, 000h, 000h, 000h, 000h, 000h, 07fh, 0dbh, 0dbh, 0dbh, 07bh, 01bh
   271 00013BB9 007FDBDBDB7B1B      <1>
   272 00013BC0 1B1B1B000000007CC6- <1>     db  01bh, 01bh, 01bh, 000h, 000h, 000h, 000h, 07ch, 0c6h, 060h, 038h, 06ch, 0c6h, 0c6h, 06ch, 038h
   272 00013BC9 60386CC6C66C38      <1>
   273 00013BD0 0CC67C000000000000- <1>     db  00ch, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 0feh, 0feh, 000h
   273 00013BD9 000000FEFEFE00      <1>
   274 00013BE0 00000000183C7E1818- <1>     db  000h, 000h, 000h, 000h, 018h, 03ch, 07eh, 018h, 018h, 018h, 07eh, 03ch, 018h, 07eh, 000h, 000h
   274 00013BE9 187E3C187E0000      <1>
   275 00013BF0 0000183C7E18181818- <1>     db  000h, 000h, 018h, 03ch, 07eh, 018h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h, 000h
   275 00013BF9 18180000000000      <1>
   276 00013C00 1818181818187E3C18- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 07eh, 03ch, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   276 00013C09 00000000000000      <1>
   277 00013C10 180CFE0C1800000000- <1>     db  018h, 00ch, 0feh, 00ch, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 030h, 060h
   277 00013C19 00000000003060      <1>
   278 00013C20 FE6030000000000000- <1>     db  0feh, 060h, 030h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0c0h, 0c0h, 0c0h
   278 00013C29 00000000C0C0C0      <1>
   279 00013C30 FE0000000000000000- <1>     db  0feh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 028h, 06ch, 0feh, 06ch, 028h, 000h
   279 00013C39 00286CFE6C2800      <1>
   280 00013C40 000000000000001038- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 010h, 038h, 038h, 07ch, 07ch, 0feh, 0feh, 000h, 000h
   280 00013C49 387C7CFEFE0000      <1>
   281 00013C50 0000000000FEFE7C7C- <1>     db  000h, 000h, 000h, 000h, 000h, 0feh, 0feh, 07ch, 07ch, 038h, 038h, 010h, 000h, 000h, 000h, 000h
   281 00013C59 38381000000000      <1>
   282 00013C60 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   282 00013C69 00000000000000      <1>
   283 00013C70 183C3C3C1818001818- <1>     db  018h, 03ch, 03ch, 03ch, 018h, 018h, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 066h, 066h, 066h
   283 00013C79 00000000666666      <1>
   284 00013C80 240000000000000000- <1>     db  024h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 06ch, 06ch, 0feh, 06ch
   284 00013C89 0000006C6CFE6C      <1>
   285 00013C90 6C6CFE6C6C00000018- <1>     db  06ch, 06ch, 0feh, 06ch, 06ch, 000h, 000h, 000h, 018h, 018h, 07ch, 0c6h, 0c2h, 0c0h, 07ch, 006h
   285 00013C99 187CC6C2C07C06      <1>
   286 00013CA0 86C67C181800000000- <1>     db  086h, 0c6h, 07ch, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 0c2h, 0c6h, 00ch, 018h, 030h, 066h
   286 00013CA9 00C2C60C183066      <1>
   287 00013CB0 C60000000000386C6C- <1>     db  0c6h, 000h, 000h, 000h, 000h, 000h, 038h, 06ch, 06ch, 038h, 076h, 0dch, 0cch, 0cch, 076h, 000h
   287 00013CB9 3876DCCCCC7600      <1>
   288 00013CC0 000000303030600000- <1>     db  000h, 000h, 000h, 030h, 030h, 030h, 060h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   288 00013CC9 00000000000000      <1>
   289 00013CD0 00000C183030303030- <1>     db  000h, 000h, 00ch, 018h, 030h, 030h, 030h, 030h, 030h, 018h, 00ch, 000h, 000h, 000h, 000h, 000h
   289 00013CD9 180C0000000000      <1>
   290 00013CE0 30180C0C0C0C0C1830- <1>     db  030h, 018h, 00ch, 00ch, 00ch, 00ch, 00ch, 018h, 030h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   290 00013CE9 00000000000000      <1>
   291 00013CF0 663CFF3C6600000000- <1>     db  066h, 03ch, 0ffh, 03ch, 066h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h
   291 00013CF9 00000000001818      <1>
   292 00013D00 7E1818000000000000- <1>     db  07eh, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   292 00013D09 00000000000000      <1>
   293 00013D10 181818300000000000- <1>     db  018h, 018h, 018h, 030h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 000h, 000h, 000h
   293 00013D19 000000FE000000      <1>
   294 00013D20 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h
   294 00013D29 00000000181800      <1>
   295 00013D30 0000000002060C1830- <1>     db  000h, 000h, 000h, 000h, 002h, 006h, 00ch, 018h, 030h, 060h, 0c0h, 080h, 000h, 000h, 000h, 000h
   295 00013D39 60C08000000000      <1>
   296 00013D40 00007CC6CEDEF6E6C6- <1>     db  000h, 000h, 07ch, 0c6h, 0ceh, 0deh, 0f6h, 0e6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h
   296 00013D49 C67C0000000000      <1>
   297 00013D50 18387818181818187E- <1>     db  018h, 038h, 078h, 018h, 018h, 018h, 018h, 018h, 07eh, 000h, 000h, 000h, 000h, 000h, 07ch, 0c6h
   297 00013D59 00000000007CC6      <1>
   298 00013D60 060C183060C6FE0000- <1>     db  006h, 00ch, 018h, 030h, 060h, 0c6h, 0feh, 000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 006h, 006h
   298 00013D69 0000007CC60606      <1>
   299 00013D70 3C0606C67C00000000- <1>     db  03ch, 006h, 006h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 00ch, 01ch, 03ch, 06ch, 0cch, 0feh
   299 00013D79 000C1C3C6CCCFE      <1>
   300 00013D80 0C0C1E0000000000FE- <1>     db  00ch, 00ch, 01eh, 000h, 000h, 000h, 000h, 000h, 0feh, 0c0h, 0c0h, 0c0h, 0fch, 006h, 006h, 0c6h
   300 00013D89 C0C0C0FC0606C6      <1>
   301 00013D90 7C00000000003860C0- <1>     db  07ch, 000h, 000h, 000h, 000h, 000h, 038h, 060h, 0c0h, 0c0h, 0fch, 0c6h, 0c6h, 0c6h, 07ch, 000h
   301 00013D99 C0FCC6C6C67C00      <1>
   302 00013DA0 00000000FEC6060C18- <1>     db  000h, 000h, 000h, 000h, 0feh, 0c6h, 006h, 00ch, 018h, 030h, 030h, 030h, 030h, 000h, 000h, 000h
   302 00013DA9 30303030000000      <1>
   303 00013DB0 00007CC6C6C67CC6C6- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 07ch, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h
   303 00013DB9 C67C0000000000      <1>
   304 00013DC0 7CC6C6C67E06060C78- <1>     db  07ch, 0c6h, 0c6h, 0c6h, 07eh, 006h, 006h, 00ch, 078h, 000h, 000h, 000h, 000h, 000h, 000h, 018h
   304 00013DC9 00000000000018      <1>
   305 00013DD0 180000001818000000- <1>     db  018h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h
   305 00013DD9 00000000181800      <1>
   306 00013DE0 000018183000000000- <1>     db  000h, 000h, 018h, 018h, 030h, 000h, 000h, 000h, 000h, 000h, 006h, 00ch, 018h, 030h, 060h, 030h
   306 00013DE9 00060C18306030      <1>
   307 00013DF0 180C06000000000000- <1>     db  018h, 00ch, 006h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07eh, 000h, 000h, 07eh, 000h
   307 00013DF9 00007E00007E00      <1>
   308 00013E00 000000000000603018- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 060h, 030h, 018h, 00ch, 006h, 00ch, 018h, 030h, 060h, 000h
   308 00013E09 0C060C18306000      <1>
   309 00013E10 000000007CC6C60C18- <1>     db  000h, 000h, 000h, 000h, 07ch, 0c6h, 0c6h, 00ch, 018h, 018h, 000h, 018h, 018h, 000h, 000h, 000h
   309 00013E19 18001818000000      <1>
   310 00013E20 00007CC6C6DEDEDEDC- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0deh, 0deh, 0deh, 0dch, 0c0h, 07ch, 000h, 000h, 000h, 000h, 000h
   310 00013E29 C07C0000000000      <1>
   311 00013E30 10386CC6C6FEC6C6C6- <1>     db  010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h, 000h, 0fch, 066h
   311 00013E39 0000000000FC66      <1>
   312 00013E40 66667C666666FC0000- <1>     db  066h, 066h, 07ch, 066h, 066h, 066h, 0fch, 000h, 000h, 000h, 000h, 000h, 03ch, 066h, 0c2h, 0c0h
   312 00013E49 0000003C66C2C0      <1>
   313 00013E50 C0C0C2663C00000000- <1>     db  0c0h, 0c0h, 0c2h, 066h, 03ch, 000h, 000h, 000h, 000h, 000h, 0f8h, 06ch, 066h, 066h, 066h, 066h
   313 00013E59 00F86C66666666      <1>
   314 00013E60 666CF80000000000FE- <1>     db  066h, 06ch, 0f8h, 000h, 000h, 000h, 000h, 000h, 0feh, 066h, 062h, 068h, 078h, 068h, 062h, 066h
   314 00013E69 66626878686266      <1>
   315 00013E70 FE0000000000FE6662- <1>     db  0feh, 000h, 000h, 000h, 000h, 000h, 0feh, 066h, 062h, 068h, 078h, 068h, 060h, 060h, 0f0h, 000h
   315 00013E79 6878686060F000      <1>
   316 00013E80 000000003C66C2C0C0- <1>     db  000h, 000h, 000h, 000h, 03ch, 066h, 0c2h, 0c0h, 0c0h, 0deh, 0c6h, 066h, 03ah, 000h, 000h, 000h
   316 00013E89 DEC6663A000000      <1>
   317 00013E90 0000C6C6C6C6FEC6C6- <1>     db  000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h, 000h
   317 00013E99 C6C60000000000      <1>
   318 00013EA0 3C181818181818183C- <1>     db  03ch, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 000h, 01eh, 00ch
   318 00013EA9 00000000001E0C      <1>
   319 00013EB0 0C0C0C0CCCCC780000- <1>     db  00ch, 00ch, 00ch, 00ch, 0cch, 0cch, 078h, 000h, 000h, 000h, 000h, 000h, 0e6h, 066h, 06ch, 06ch
   319 00013EB9 000000E6666C6C      <1>
   320 00013EC0 786C6C66E600000000- <1>     db  078h, 06ch, 06ch, 066h, 0e6h, 000h, 000h, 000h, 000h, 000h, 0f0h, 060h, 060h, 060h, 060h, 060h
   320 00013EC9 00F06060606060      <1>
   321 00013ED0 6266FE0000000000C6- <1>     db  062h, 066h, 0feh, 000h, 000h, 000h, 000h, 000h, 0c6h, 0eeh, 0feh, 0feh, 0d6h, 0c6h, 0c6h, 0c6h
   321 00013ED9 EEFEFED6C6C6C6      <1>
   322 00013EE0 C60000000000C6E6F6- <1>     db  0c6h, 000h, 000h, 000h, 000h, 000h, 0c6h, 0e6h, 0f6h, 0feh, 0deh, 0ceh, 0c6h, 0c6h, 0c6h, 000h
   322 00013EE9 FEDECEC6C6C600      <1>
   323 00013EF0 00000000386CC6C6C6- <1>     db  000h, 000h, 000h, 000h, 038h, 06ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 06ch, 038h, 000h, 000h, 000h
   323 00013EF9 C6C66C38000000      <1>
   324 00013F00 0000FC6666667C6060- <1>     db  000h, 000h, 0fch, 066h, 066h, 066h, 07ch, 060h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h, 000h
   324 00013F09 60F00000000000      <1>
   325 00013F10 7CC6C6C6C6D6DE7C0C- <1>     db  07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0d6h, 0deh, 07ch, 00ch, 00eh, 000h, 000h, 000h, 000h, 0fch, 066h
   325 00013F19 0E00000000FC66      <1>
   326 00013F20 66667C6C6666E60000- <1>     db  066h, 066h, 07ch, 06ch, 066h, 066h, 0e6h, 000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0c6h, 060h
   326 00013F29 0000007CC6C660      <1>
   327 00013F30 380CC6C67C00000000- <1>     db  038h, 00ch, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 07eh, 07eh, 05ah, 018h, 018h, 018h
   327 00013F39 007E7E5A181818      <1>
   328 00013F40 18183C0000000000C6- <1>     db  018h, 018h, 03ch, 000h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h
   328 00013F49 C6C6C6C6C6C6C6      <1>
   329 00013F50 7C0000000000C6C6C6- <1>     db  07ch, 000h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 06ch, 038h, 010h, 000h
   329 00013F59 C6C6C66C381000      <1>
   330 00013F60 00000000C6C6C6C6D6- <1>     db  000h, 000h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0d6h, 0d6h, 0feh, 07ch, 06ch, 000h, 000h, 000h
   330 00013F69 D6FE7C6C000000      <1>
   331 00013F70 0000C6C66C3838386C- <1>     db  000h, 000h, 0c6h, 0c6h, 06ch, 038h, 038h, 038h, 06ch, 0c6h, 0c6h, 000h, 000h, 000h, 000h, 000h
   331 00013F79 C6C60000000000      <1>
   332 00013F80 666666663C1818183C- <1>     db  066h, 066h, 066h, 066h, 03ch, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 000h, 0feh, 0c6h
   332 00013F89 0000000000FEC6      <1>
   333 00013F90 8C183060C2C6FE0000- <1>     db  08ch, 018h, 030h, 060h, 0c2h, 0c6h, 0feh, 000h, 000h, 000h, 000h, 000h, 03ch, 030h, 030h, 030h
   333 00013F99 0000003C303030      <1>
   334 00013FA0 303030303C00000000- <1>     db  030h, 030h, 030h, 030h, 03ch, 000h, 000h, 000h, 000h, 000h, 080h, 0c0h, 0e0h, 070h, 038h, 01ch
   334 00013FA9 0080C0E070381C      <1>
   335 00013FB0 0E060200000000003C- <1>     db  00eh, 006h, 002h, 000h, 000h, 000h, 000h, 000h, 03ch, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch
   335 00013FB9 0C0C0C0C0C0C0C      <1>
   336 00013FC0 3C00000010386CC600- <1>     db  03ch, 000h, 000h, 000h, 010h, 038h, 06ch, 0c6h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   336 00013FC9 00000000000000      <1>
   337 00013FD0 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h
   337 00013FD9 0000000000FF00      <1>
   338 00013FE0 303018000000000000- <1>     db  030h, 030h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   338 00013FE9 00000000000000      <1>
   339 00013FF0 000000780C7CCCCC76- <1>     db  000h, 000h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 000h, 0e0h, 060h
   339 00013FF9 0000000000E060      <1>
   340 00014000 60786C6666667C0000- <1>     db  060h, 078h, 06ch, 066h, 066h, 066h, 07ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07ch
   340 00014009 0000000000007C      <1>
   341 00014010 C6C0C0C67C00000000- <1>     db  0c6h, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 01ch, 00ch, 00ch, 03ch, 06ch, 0cch
   341 00014019 001C0C0C3C6CCC      <1>
   342 00014020 CCCC76000000000000- <1>     db  0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c6h
   342 00014029 00007CC6FEC0C6      <1>
   343 00014030 7C0000000000386C64- <1>     db  07ch, 000h, 000h, 000h, 000h, 000h, 038h, 06ch, 064h, 060h, 0f0h, 060h, 060h, 060h, 0f0h, 000h
   343 00014039 60F0606060F000      <1>
   344 00014040 0000000000000076CC- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 076h, 0cch, 0cch, 0cch, 07ch, 00ch, 0cch, 078h, 000h
   344 00014049 CCCC7C0CCC7800      <1>
   345 00014050 0000E060606C766666- <1>     db  000h, 000h, 0e0h, 060h, 060h, 06ch, 076h, 066h, 066h, 066h, 0e6h, 000h, 000h, 000h, 000h, 000h
   345 00014059 66E60000000000      <1>
   346 00014060 18180038181818183C- <1>     db  018h, 018h, 000h, 038h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 000h, 006h, 006h
   346 00014069 00000000000606      <1>
   347 00014070 000E0606060666663C- <1>     db  000h, 00eh, 006h, 006h, 006h, 006h, 066h, 066h, 03ch, 000h, 000h, 000h, 0e0h, 060h, 060h, 066h
   347 00014079 000000E0606066      <1>
   348 00014080 6C786C66E600000000- <1>     db  06ch, 078h, 06ch, 066h, 0e6h, 000h, 000h, 000h, 000h, 000h, 038h, 018h, 018h, 018h, 018h, 018h
   348 00014089 00381818181818      <1>
   349 00014090 18183C000000000000- <1>     db  018h, 018h, 03ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ech, 0feh, 0d6h, 0d6h, 0d6h
   349 00014099 0000ECFED6D6D6      <1>
   350 000140A0 C60000000000000000- <1>     db  0c6h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0dch, 066h, 066h, 066h, 066h, 066h, 000h
   350 000140A9 DC666666666600      <1>
   351 000140B0 000000000000007CC6- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h
   351 000140B9 C6C6C67C000000      <1>
   352 000140C0 0000000000DC666666- <1>     db  000h, 000h, 000h, 000h, 000h, 0dch, 066h, 066h, 066h, 07ch, 060h, 060h, 0f0h, 000h, 000h, 000h
   352 000140C9 7C6060F0000000      <1>
   353 000140D0 00000076CCCCCC7C0C- <1>     db  000h, 000h, 000h, 076h, 0cch, 0cch, 0cch, 07ch, 00ch, 00ch, 01eh, 000h, 000h, 000h, 000h, 000h
   353 000140D9 0C1E0000000000      <1>
   354 000140E0 00DC76666060F00000- <1>     db  000h, 0dch, 076h, 066h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07ch
   354 000140E9 0000000000007C      <1>
   355 000140F0 C6701CC67C00000000- <1>     db  0c6h, 070h, 01ch, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 010h, 030h, 030h, 0fch, 030h, 030h
   355 000140F9 00103030FC3030      <1>
   356 00014100 30361C000000000000- <1>     db  030h, 036h, 01ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch
   356 00014109 0000CCCCCCCCCC      <1>
   357 00014110 760000000000000000- <1>     db  076h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 066h, 066h, 066h, 066h, 03ch, 018h, 000h
   357 00014119 666666663C1800      <1>
   358 00014120 00000000000000C6C6- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 0d6h, 0d6h, 0feh, 06ch, 000h, 000h, 000h
   358 00014129 D6D6FE6C000000      <1>
   359 00014130 0000000000C66C3838- <1>     db  000h, 000h, 000h, 000h, 000h, 0c6h, 06ch, 038h, 038h, 06ch, 0c6h, 000h, 000h, 000h, 000h, 000h
   359 00014139 6CC60000000000      <1>
   360 00014140 000000C6C6C6C67E06- <1>     db  000h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 07eh, 006h, 00ch, 0f8h, 000h, 000h, 000h, 000h, 000h
   360 00014149 0CF80000000000      <1>
   361 00014150 00FECC183066FE0000- <1>     db  000h, 0feh, 0cch, 018h, 030h, 066h, 0feh, 000h, 000h, 000h, 000h, 000h, 00eh, 018h, 018h, 018h
   361 00014159 0000000E181818      <1>
   362 00014160 701818180E00000000- <1>     db  070h, 018h, 018h, 018h, 00eh, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 000h, 018h
   362 00014169 00181818180018      <1>
   363 00014170 181818000000000070- <1>     db  018h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 070h, 018h, 018h, 018h, 00eh, 018h, 018h, 018h
   363 00014179 1818180E181818      <1>
   364 00014180 70000000000076DC00- <1>     db  070h, 000h, 000h, 000h, 000h, 000h, 076h, 0dch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   364 00014189 00000000000000      <1>
   365 00014190 00000000000010386C- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 000h, 000h, 000h, 000h
   365 00014199 C6C6FE00000000      <1>
   366 000141A0 00003C66C2C0C0C266- <1>     db  000h, 000h, 03ch, 066h, 0c2h, 0c0h, 0c0h, 0c2h, 066h, 03ch, 00ch, 006h, 07ch, 000h, 000h, 000h
   366 000141A9 3C0C067C000000      <1>
   367 000141B0 CCCC00CCCCCCCCCC76- <1>     db  0cch, 0cch, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 00ch, 018h, 030h
   367 000141B9 000000000C1830      <1>
   368 000141C0 007CC6FEC0C67C0000- <1>     db  000h, 07ch, 0c6h, 0feh, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 010h, 038h, 06ch, 000h, 078h
   368 000141C9 000010386C0078      <1>
   369 000141D0 0C7CCCCC7600000000- <1>     db  00ch, 07ch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 000h, 0cch, 0cch, 000h, 078h, 00ch, 07ch
   369 000141D9 00CCCC00780C7C      <1>
   370 000141E0 CCCC76000000006030- <1>     db  0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 060h, 030h, 018h, 000h, 078h, 00ch, 07ch, 0cch, 0cch
   370 000141E9 1800780C7CCCCC      <1>
   371 000141F0 7600000000386C3800- <1>     db  076h, 000h, 000h, 000h, 000h, 038h, 06ch, 038h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 076h, 000h
   371 000141F9 780C7CCCCC7600      <1>
   372 00014200 0000000000003C6660- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 03ch, 066h, 060h, 066h, 03ch, 00ch, 006h, 03ch, 000h, 000h
   372 00014209 663C0C063C0000      <1>
   373 00014210 0010386C007CC6FEC0- <1>     db  000h, 010h, 038h, 06ch, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h
   373 00014219 C67C0000000000      <1>
   374 00014220 CCCC007CC6FEC0C67C- <1>     db  0cch, 0cch, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 060h, 030h, 018h
   374 00014229 00000000603018      <1>
   375 00014230 007CC6FEC0C67C0000- <1>     db  000h, 07ch, 0c6h, 0feh, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 066h, 066h, 000h, 038h
   375 00014239 00000066660038      <1>
   376 00014240 181818183C00000000- <1>     db  018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 018h, 03ch, 066h, 000h, 038h, 018h, 018h
   376 00014249 183C6600381818      <1>
   377 00014250 18183C000000006030- <1>     db  018h, 018h, 03ch, 000h, 000h, 000h, 000h, 060h, 030h, 018h, 000h, 038h, 018h, 018h, 018h, 018h
   377 00014259 18003818181818      <1>
   378 00014260 3C00000000C6C61038- <1>     db  03ch, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 000h
   378 00014269 6CC6C6FEC6C600      <1>
   379 00014270 0000386C3800386CC6- <1>     db  000h, 000h, 038h, 06ch, 038h, 000h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 000h, 000h, 000h
   379 00014279 C6FEC6C6000000      <1>
   380 00014280 18306000FE66607C60- <1>     db  018h, 030h, 060h, 000h, 0feh, 066h, 060h, 07ch, 060h, 066h, 0feh, 000h, 000h, 000h, 000h, 000h
   380 00014289 66FE0000000000      <1>
   381 00014290 0000CC76367ED8D86E- <1>     db  000h, 000h, 0cch, 076h, 036h, 07eh, 0d8h, 0d8h, 06eh, 000h, 000h, 000h, 000h, 000h, 03eh, 06ch
   381 00014299 00000000003E6C      <1>
   382 000142A0 CCCCFECCCCCCCE0000- <1>     db  0cch, 0cch, 0feh, 0cch, 0cch, 0cch, 0ceh, 000h, 000h, 000h, 000h, 010h, 038h, 06ch, 000h, 07ch
   382 000142A9 000010386C007C      <1>
   383 000142B0 C6C6C6C67C00000000- <1>     db  0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 000h, 07ch, 0c6h, 0c6h
   383 000142B9 00C6C6007CC6C6      <1>
   384 000142C0 C6C67C000000006030- <1>     db  0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 060h, 030h, 018h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h
   384 000142C9 18007CC6C6C6C6      <1>
   385 000142D0 7C000000003078CC00- <1>     db  07ch, 000h, 000h, 000h, 000h, 030h, 078h, 0cch, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h
   385 000142D9 CCCCCCCCCC7600      <1>
   386 000142E0 00000060301800CCCC- <1>     db  000h, 000h, 000h, 060h, 030h, 018h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h
   386 000142E9 CCCCCC76000000      <1>
   387 000142F0 0000C6C600C6C6C6C6- <1>     db  000h, 000h, 0c6h, 0c6h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 07eh, 006h, 00ch, 078h, 000h, 000h, 0c6h
   387 000142F9 7E060C780000C6      <1>
   388 00014300 C6386CC6C6C6C66C38- <1>     db  0c6h, 038h, 06ch, 0c6h, 0c6h, 0c6h, 0c6h, 06ch, 038h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 000h
   388 00014309 00000000C6C600      <1>
   389 00014310 C6C6C6C6C6C67C0000- <1>     db  0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 018h, 018h, 03ch, 066h, 060h
   389 00014319 000018183C6660      <1>
   390 00014320 60663C181800000000- <1>     db  060h, 066h, 03ch, 018h, 018h, 000h, 000h, 000h, 000h, 038h, 06ch, 064h, 060h, 0f0h, 060h, 060h
   390 00014329 386C6460F06060      <1>
   391 00014330 60E6FC000000000066- <1>     db  060h, 0e6h, 0fch, 000h, 000h, 000h, 000h, 000h, 066h, 066h, 03ch, 018h, 07eh, 018h, 07eh, 018h
   391 00014339 663C187E187E18      <1>
   392 00014340 1800000000F8CCCCF8- <1>     db  018h, 000h, 000h, 000h, 000h, 0f8h, 0cch, 0cch, 0f8h, 0c4h, 0cch, 0deh, 0cch, 0cch, 0c6h, 000h
   392 00014349 C4CCDECCCCC600      <1>
   393 00014350 0000000E1B1818187E- <1>     db  000h, 000h, 000h, 00eh, 01bh, 018h, 018h, 018h, 07eh, 018h, 018h, 018h, 018h, 0d8h, 070h, 000h
   393 00014359 18181818D87000      <1>
   394 00014360 0018306000780C7CCC- <1>     db  000h, 018h, 030h, 060h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 00ch
   394 00014369 CC76000000000C      <1>
   395 00014370 18300038181818183C- <1>     db  018h, 030h, 000h, 038h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 018h, 030h, 060h
   395 00014379 00000000183060      <1>
   396 00014380 007CC6C6C6C67C0000- <1>     db  000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 018h, 030h, 060h, 000h, 0cch
   396 00014389 000018306000CC      <1>
   397 00014390 CCCCCCCC7600000000- <1>     db  0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h, 000h, 076h, 0dch, 000h, 0dch, 066h, 066h
   397 00014399 0076DC00DC6666      <1>
   398 000143A0 66666600000076DC00- <1>     db  066h, 066h, 066h, 000h, 000h, 000h, 076h, 0dch, 000h, 0c6h, 0e6h, 0f6h, 0feh, 0deh, 0ceh, 0c6h
   398 000143A9 C6E6F6FEDECEC6      <1>
   399 000143B0 C6000000003C6C6C3E- <1>     db  0c6h, 000h, 000h, 000h, 000h, 03ch, 06ch, 06ch, 03eh, 000h, 07eh, 000h, 000h, 000h, 000h, 000h
   399 000143B9 007E0000000000      <1>
   400 000143C0 000000386C6C38007C- <1>     db  000h, 000h, 000h, 038h, 06ch, 06ch, 038h, 000h, 07ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   400 000143C9 00000000000000      <1>
   401 000143D0 0000303000303060C6- <1>     db  000h, 000h, 030h, 030h, 000h, 030h, 030h, 060h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h, 000h
   401 000143D9 C67C0000000000      <1>
   402 000143E0 00000000FEC0C0C000- <1>     db  000h, 000h, 000h, 000h, 0feh, 0c0h, 0c0h, 0c0h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   402 000143E9 00000000000000      <1>
   403 000143F0 0000FE060606000000- <1>     db  000h, 000h, 0feh, 006h, 006h, 006h, 000h, 000h, 000h, 000h, 000h, 0c0h, 0c0h, 0c6h, 0cch, 0d8h
   403 000143F9 0000C0C0C6CCD8      <1>
   404 00014400 3060DC860C183E0000- <1>     db  030h, 060h, 0dch, 086h, 00ch, 018h, 03eh, 000h, 000h, 0c0h, 0c0h, 0c6h, 0cch, 0d8h, 030h, 066h
   404 00014409 C0C0C6CCD83066      <1>
   405 00014410 CE9E3E060600000018- <1>     db  0ceh, 09eh, 03eh, 006h, 006h, 000h, 000h, 000h, 018h, 018h, 000h, 018h, 018h, 03ch, 03ch, 03ch
   405 00014419 180018183C3C3C      <1>
   406 00014420 180000000000000036- <1>     db  018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 036h, 06ch, 0d8h, 06ch, 036h, 000h, 000h, 000h
   406 00014429 6CD86C36000000      <1>
   407 00014430 000000000000D86C36- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 0d8h, 06ch, 036h, 06ch, 0d8h, 000h, 000h, 000h, 000h, 000h
   407 00014439 6CD80000000000      <1>
   408 00014440 114411441144114411- <1>     db  011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 055h, 0aah
   408 00014449 441144114455AA      <1>
   409 00014450 55AA55AA55AA55AA55- <1>     db  055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 0ddh, 077h, 0ddh, 077h
   409 00014459 AA55AADD77DD77      <1>
   410 00014460 DD77DD77DD77DD77DD- <1>     db  0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 018h, 018h, 018h, 018h, 018h, 018h
   410 00014469 77181818181818      <1>
   411 00014470 181818181818181818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0f8h
   411 00014479 181818181818F8      <1>
   412 00014480 181818181818181818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 0f8h, 018h, 018h
   412 00014489 1818F818F81818      <1>
   413 00014490 181818183636363636- <1>     db  018h, 018h, 018h, 018h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 0f6h, 036h, 036h, 036h, 036h
   413 00014499 3636F636363636      <1>
   414 000144A0 363600000000000000- <1>     db  036h, 036h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 036h, 036h, 036h, 036h, 036h, 036h
   414 000144A9 FE363636363636      <1>
   415 000144B0 0000000000F818F818- <1>     db  000h, 000h, 000h, 000h, 000h, 0f8h, 018h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h, 036h, 036h
   415 000144B9 18181818183636      <1>
   416 000144C0 363636F606F6363636- <1>     db  036h, 036h, 036h, 0f6h, 006h, 0f6h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   416 000144C9 36363636363636      <1>
   417 000144D0 363636363636363636- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 000h, 000h, 000h, 000h, 000h, 0feh
   417 000144D9 360000000000FE      <1>
   418 000144E0 06F636363636363636- <1>     db  006h, 0f6h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 0f6h, 006h, 0feh
   418 000144E9 36363636F606FE      <1>
   419 000144F0 000000000000363636- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 0feh, 000h, 000h
   419 000144F9 36363636FE0000      <1>
   420 00014500 000000001818181818- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 0f8h, 000h, 000h, 000h, 000h
   420 00014509 F818F800000000      <1>
   421 00014510 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h
   421 00014519 F8181818181818      <1>
   422 00014520 181818181818181F00- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 01fh, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h
   422 00014529 00000000001818      <1>
   423 00014530 1818181818FF000000- <1>     db  018h, 018h, 018h, 018h, 018h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   423 00014539 00000000000000      <1>
   424 00014540 000000FF1818181818- <1>     db  000h, 000h, 000h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   424 00014549 18181818181818      <1>
   425 00014550 181F18181818181800- <1>     db  018h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh
   425 00014559 000000000000FF      <1>
   426 00014560 000000000000181818- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0ffh, 018h, 018h
   426 00014569 18181818FF1818      <1>
   427 00014570 181818181818181818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 01fh, 018h, 01fh, 018h, 018h, 018h, 018h
   427 00014579 1F181F18181818      <1>
   428 00014580 181836363636363636- <1>     db  018h, 018h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 037h, 036h, 036h, 036h, 036h, 036h, 036h
   428 00014589 37363636363636      <1>
   429 00014590 363636363637303F00- <1>     db  036h, 036h, 036h, 036h, 036h, 037h, 030h, 03fh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   429 00014599 00000000000000      <1>
   430 000145A0 0000003F3037363636- <1>     db  000h, 000h, 000h, 03fh, 030h, 037h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   430 000145A9 36363636363636      <1>
   431 000145B0 36F700FF0000000000- <1>     db  036h, 0f7h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh
   431 000145B9 000000000000FF      <1>
   432 000145C0 00F736363636363636- <1>     db  000h, 0f7h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 037h, 030h, 037h
   432 000145C9 36363636373037      <1>
   433 000145D0 363636363636000000- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0ffh, 000h, 000h
   433 000145D9 0000FF00FF0000      <1>
   434 000145E0 000000003636363636- <1>     db  000h, 000h, 000h, 000h, 036h, 036h, 036h, 036h, 036h, 0f7h, 000h, 0f7h, 036h, 036h, 036h, 036h
   434 000145E9 F700F736363636      <1>
   435 000145F0 36361818181818FF00- <1>     db  036h, 036h, 018h, 018h, 018h, 018h, 018h, 0ffh, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h
   435 000145F9 FF000000000000      <1>
   436 00014600 36363636363636FF00- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   436 00014609 00000000000000      <1>
   437 00014610 000000FF00FF181818- <1>     db  000h, 000h, 000h, 0ffh, 000h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   437 00014619 18181800000000      <1>
   438 00014620 000000FF3636363636- <1>     db  000h, 000h, 000h, 0ffh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   438 00014629 36363636363636      <1>
   439 00014630 363F00000000000018- <1>     db  036h, 03fh, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 018h, 018h, 018h, 01fh, 018h, 01fh
   439 00014639 181818181F181F      <1>
   440 00014640 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 01fh, 018h, 01fh, 018h, 018h
   440 00014649 00001F181F1818      <1>
   441 00014650 181818180000000000- <1>     db  018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 03fh, 036h, 036h, 036h, 036h
   441 00014659 00003F36363636      <1>
   442 00014660 363636363636363636- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 0ffh, 036h, 036h, 036h, 036h, 036h, 036h
   442 00014669 FF363636363636      <1>
   443 00014670 1818181818FF18FF18- <1>     db  018h, 018h, 018h, 018h, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   443 00014679 18181818181818      <1>
   444 00014680 1818181818F8000000- <1>     db  018h, 018h, 018h, 018h, 018h, 0f8h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   444 00014689 00000000000000      <1>
   445 00014690 0000001F1818181818- <1>     db  000h, 000h, 000h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   445 00014699 18FFFFFFFFFFFF      <1>
   446 000146A0 FFFFFFFFFFFFFFFF00- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh
   446 000146A9 000000000000FF      <1>
   447 000146B0 FFFFFFFFFFFFF0F0F0- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h
   447 000146B9 F0F0F0F0F0F0F0      <1>
   448 000146C0 F0F0F0F00F0F0F0F0F- <1>     db  0f0h, 0f0h, 0f0h, 0f0h, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh
   448 000146C9 0F0F0F0F0F0F0F      <1>
   449 000146D0 0F0FFFFFFFFFFFFFFF- <1>     db  00fh, 00fh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   449 000146D9 00000000000000      <1>
   450 000146E0 000000000076DCD8D8- <1>     db  000h, 000h, 000h, 000h, 000h, 076h, 0dch, 0d8h, 0d8h, 0dch, 076h, 000h, 000h, 000h, 000h, 000h
   450 000146E9 DC760000000000      <1>
   451 000146F0 00007CC6FCC6C6FCC0- <1>     db  000h, 000h, 07ch, 0c6h, 0fch, 0c6h, 0c6h, 0fch, 0c0h, 0c0h, 040h, 000h, 000h, 000h, 0feh, 0c6h
   451 000146F9 C040000000FEC6      <1>
   452 00014700 C6C0C0C0C0C0C00000- <1>     db  0c6h, 0c0h, 0c0h, 0c0h, 0c0h, 0c0h, 0c0h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 06ch
   452 00014709 0000000000FE6C      <1>
   453 00014710 6C6C6C6C6C00000000- <1>     db  06ch, 06ch, 06ch, 06ch, 06ch, 000h, 000h, 000h, 000h, 000h, 0feh, 0c6h, 060h, 030h, 018h, 030h
   453 00014719 00FEC660301830      <1>
   454 00014720 60C6FE000000000000- <1>     db  060h, 0c6h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07eh, 0d8h, 0d8h, 0d8h, 0d8h
   454 00014729 00007ED8D8D8D8      <1>
   455 00014730 700000000000000066- <1>     db  070h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 066h, 066h, 066h, 066h, 07ch, 060h, 060h, 0c0h
   455 00014739 6666667C6060C0      <1>
   456 00014740 00000000000076DC18- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 076h, 0dch, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h
   456 00014749 18181818000000      <1>
   457 00014750 00007E183C6666663C- <1>     db  000h, 000h, 07eh, 018h, 03ch, 066h, 066h, 066h, 03ch, 018h, 07eh, 000h, 000h, 000h, 000h, 000h
   457 00014759 187E0000000000      <1>
   458 00014760 386CC6C6FEC6C66C38- <1>     db  038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 06ch, 038h, 000h, 000h, 000h, 000h, 000h, 038h, 06ch
   458 00014769 0000000000386C      <1>
   459 00014770 C6C6C66C6C6CEE0000- <1>     db  0c6h, 0c6h, 0c6h, 06ch, 06ch, 06ch, 0eeh, 000h, 000h, 000h, 000h, 000h, 01eh, 030h, 018h, 00ch
   459 00014779 0000001E30180C      <1>
   460 00014780 3E6666663C00000000- <1>     db  03eh, 066h, 066h, 066h, 03ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07eh, 0dbh, 0dbh
   460 00014789 000000007EDBDB      <1>
   461 00014790 7E0000000000000003- <1>     db  07eh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 003h, 006h, 07eh, 0dbh, 0dbh, 0f3h, 07eh, 060h
   461 00014799 067EDBDBF37E60      <1>
   462 000147A0 C000000000001C3060- <1>     db  0c0h, 000h, 000h, 000h, 000h, 000h, 01ch, 030h, 060h, 060h, 07ch, 060h, 060h, 030h, 01ch, 000h
   462 000147A9 607C6060301C00      <1>
   463 000147B0 00000000007CC6C6C6- <1>     db  000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h
   463 000147B9 C6C6C6C6000000      <1>
   464 000147C0 000000FE0000FE0000- <1>     db  000h, 000h, 000h, 0feh, 000h, 000h, 0feh, 000h, 000h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h
   464 000147C9 FE000000000000      <1>
   465 000147D0 0018187E18180000FF- <1>     db  000h, 018h, 018h, 07eh, 018h, 018h, 000h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 030h, 018h
   465 000147D9 00000000003018      <1>
   466 000147E0 0C060C1830007E0000- <1>     db  00ch, 006h, 00ch, 018h, 030h, 000h, 07eh, 000h, 000h, 000h, 000h, 000h, 00ch, 018h, 030h, 060h
   466 000147E9 0000000C183060      <1>
   467 000147F0 30180C007E00000000- <1>     db  030h, 018h, 00ch, 000h, 07eh, 000h, 000h, 000h, 000h, 000h, 00eh, 01bh, 01bh, 018h, 018h, 018h
   467 000147F9 000E1B1B181818      <1>
   468 00014800 181818181818181818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0d8h, 0d8h
   468 00014809 1818181818D8D8      <1>
   469 00014810 700000000000001818- <1>     db  070h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h, 07eh, 000h, 018h, 018h, 000h, 000h
   469 00014819 007E0018180000      <1>
   470 00014820 00000000000076DC00- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 076h, 0dch, 000h, 076h, 0dch, 000h, 000h, 000h, 000h, 000h
   470 00014829 76DC0000000000      <1>
   471 00014830 00386C6C3800000000- <1>     db  000h, 038h, 06ch, 06ch, 038h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   471 00014839 00000000000000      <1>
   472 00014840 000000001818000000- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   472 00014849 00000000000000      <1>
   473 00014850 000000180000000000- <1>     db  000h, 000h, 000h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 00fh, 00ch, 00ch, 00ch, 00ch
   473 00014859 00000F0C0C0C0C      <1>
   474 00014860 0CEC6C3C1C00000000- <1>     db  00ch, 0ech, 06ch, 03ch, 01ch, 000h, 000h, 000h, 000h, 0d8h, 06ch, 06ch, 06ch, 06ch, 06ch, 000h
   474 00014869 D86C6C6C6C6C00      <1>
   475 00014870 0000000000000070D8- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 070h, 0d8h, 030h, 060h, 0c8h, 0f8h, 000h, 000h, 000h
   475 00014879 3060C8F8000000      <1>
   476 00014880 00000000000000007C- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 07ch, 07ch, 07ch, 07ch, 07ch, 07ch, 000h, 000h
   476 00014889 7C7C7C7C7C0000      <1>
   477 00014890 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   477 00014899 00000000000000      <1>
   478                              <1> vgafont16:
   479 000148A0 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   479 000148A9 00000000000000      <1>
   480 000148B0 00007E81A58181BD99- <1>     db  000h, 000h, 07eh, 081h, 0a5h, 081h, 081h, 0bdh, 099h, 081h, 081h, 07eh, 000h, 000h, 000h, 000h
   480 000148B9 81817E00000000      <1>
   481 000148C0 00007EFFDBFFFFC3E7- <1>     db  000h, 000h, 07eh, 0ffh, 0dbh, 0ffh, 0ffh, 0c3h, 0e7h, 0ffh, 0ffh, 07eh, 000h, 000h, 000h, 000h
   481 000148C9 FFFF7E00000000      <1>
   482 000148D0 000000006CFEFEFEFE- <1>     db  000h, 000h, 000h, 000h, 06ch, 0feh, 0feh, 0feh, 0feh, 07ch, 038h, 010h, 000h, 000h, 000h, 000h
   482 000148D9 7C381000000000      <1>
   483 000148E0 0000000010387CFE7C- <1>     db  000h, 000h, 000h, 000h, 010h, 038h, 07ch, 0feh, 07ch, 038h, 010h, 000h, 000h, 000h, 000h, 000h
   483 000148E9 38100000000000      <1>
   484 000148F0 000000183C3CE7E7E7- <1>     db  000h, 000h, 000h, 018h, 03ch, 03ch, 0e7h, 0e7h, 0e7h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   484 000148F9 18183C00000000      <1>
   485 00014900 000000183C7EFFFF7E- <1>     db  000h, 000h, 000h, 018h, 03ch, 07eh, 0ffh, 0ffh, 07eh, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   485 00014909 18183C00000000      <1>
   486 00014910 000000000000183C3C- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 018h, 03ch, 03ch, 018h, 000h, 000h, 000h, 000h, 000h, 000h
   486 00014919 18000000000000      <1>
   487 00014920 FFFFFFFFFFFFE7C3C3- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0e7h, 0c3h, 0c3h, 0e7h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   487 00014929 E7FFFFFFFFFFFF      <1>
   488 00014930 00000000003C664242- <1>     db  000h, 000h, 000h, 000h, 000h, 03ch, 066h, 042h, 042h, 066h, 03ch, 000h, 000h, 000h, 000h, 000h
   488 00014939 663C0000000000      <1>
   489 00014940 FFFFFFFFFFC399BDBD- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0c3h, 099h, 0bdh, 0bdh, 099h, 0c3h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   489 00014949 99C3FFFFFFFFFF      <1>
   490 00014950 00001E0E1A3278CCCC- <1>     db  000h, 000h, 01eh, 00eh, 01ah, 032h, 078h, 0cch, 0cch, 0cch, 0cch, 078h, 000h, 000h, 000h, 000h
   490 00014959 CCCC7800000000      <1>
   491 00014960 00003C666666663C18- <1>     db  000h, 000h, 03ch, 066h, 066h, 066h, 066h, 03ch, 018h, 07eh, 018h, 018h, 000h, 000h, 000h, 000h
   491 00014969 7E181800000000      <1>
   492 00014970 00003F333F30303030- <1>     db  000h, 000h, 03fh, 033h, 03fh, 030h, 030h, 030h, 030h, 070h, 0f0h, 0e0h, 000h, 000h, 000h, 000h
   492 00014979 70F0E000000000      <1>
   493 00014980 00007F637F63636363- <1>     db  000h, 000h, 07fh, 063h, 07fh, 063h, 063h, 063h, 063h, 067h, 0e7h, 0e6h, 0c0h, 000h, 000h, 000h
   493 00014989 67E7E6C0000000      <1>
   494 00014990 0000001818DB3CE73C- <1>     db  000h, 000h, 000h, 018h, 018h, 0dbh, 03ch, 0e7h, 03ch, 0dbh, 018h, 018h, 000h, 000h, 000h, 000h
   494 00014999 DB181800000000      <1>
   495 000149A0 0080C0E0F0F8FEF8F0- <1>     db  000h, 080h, 0c0h, 0e0h, 0f0h, 0f8h, 0feh, 0f8h, 0f0h, 0e0h, 0c0h, 080h, 000h, 000h, 000h, 000h
   495 000149A9 E0C08000000000      <1>
   496 000149B0 0002060E1E3EFE3E1E- <1>     db  000h, 002h, 006h, 00eh, 01eh, 03eh, 0feh, 03eh, 01eh, 00eh, 006h, 002h, 000h, 000h, 000h, 000h
   496 000149B9 0E060200000000      <1>
   497 000149C0 0000183C7E1818187E- <1>     db  000h, 000h, 018h, 03ch, 07eh, 018h, 018h, 018h, 07eh, 03ch, 018h, 000h, 000h, 000h, 000h, 000h
   497 000149C9 3C180000000000      <1>
   498 000149D0 000066666666666666- <1>     db  000h, 000h, 066h, 066h, 066h, 066h, 066h, 066h, 066h, 000h, 066h, 066h, 000h, 000h, 000h, 000h
   498 000149D9 00666600000000      <1>
   499 000149E0 00007FDBDBDB7B1B1B- <1>     db  000h, 000h, 07fh, 0dbh, 0dbh, 0dbh, 07bh, 01bh, 01bh, 01bh, 01bh, 01bh, 000h, 000h, 000h, 000h
   499 000149E9 1B1B1B00000000      <1>
   500 000149F0 007CC660386CC6C66C- <1>     db  000h, 07ch, 0c6h, 060h, 038h, 06ch, 0c6h, 0c6h, 06ch, 038h, 00ch, 0c6h, 07ch, 000h, 000h, 000h
   500 000149F9 380CC67C000000      <1>
   501 00014A00 0000000000000000FE- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 0feh, 0feh, 0feh, 000h, 000h, 000h, 000h
   501 00014A09 FEFEFE00000000      <1>
   502 00014A10 0000183C7E1818187E- <1>     db  000h, 000h, 018h, 03ch, 07eh, 018h, 018h, 018h, 07eh, 03ch, 018h, 07eh, 000h, 000h, 000h, 000h
   502 00014A19 3C187E00000000      <1>
   503 00014A20 0000183C7E18181818- <1>     db  000h, 000h, 018h, 03ch, 07eh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   503 00014A29 18181800000000      <1>
   504 00014A30 000018181818181818- <1>     db  000h, 000h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 07eh, 03ch, 018h, 000h, 000h, 000h, 000h
   504 00014A39 7E3C1800000000      <1>
   505 00014A40 0000000000180CFE0C- <1>     db  000h, 000h, 000h, 000h, 000h, 018h, 00ch, 0feh, 00ch, 018h, 000h, 000h, 000h, 000h, 000h, 000h
   505 00014A49 18000000000000      <1>
   506 00014A50 00000000003060FE60- <1>     db  000h, 000h, 000h, 000h, 000h, 030h, 060h, 0feh, 060h, 030h, 000h, 000h, 000h, 000h, 000h, 000h
   506 00014A59 30000000000000      <1>
   507 00014A60 000000000000C0C0C0- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 0c0h, 0c0h, 0c0h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h
   507 00014A69 FE000000000000      <1>
   508 00014A70 00000000002466FF66- <1>     db  000h, 000h, 000h, 000h, 000h, 024h, 066h, 0ffh, 066h, 024h, 000h, 000h, 000h, 000h, 000h, 000h
   508 00014A79 24000000000000      <1>
   509 00014A80 000000001038387C7C- <1>     db  000h, 000h, 000h, 000h, 010h, 038h, 038h, 07ch, 07ch, 0feh, 0feh, 000h, 000h, 000h, 000h, 000h
   509 00014A89 FEFE0000000000      <1>
   510 00014A90 00000000FEFE7C7C38- <1>     db  000h, 000h, 000h, 000h, 0feh, 0feh, 07ch, 07ch, 038h, 038h, 010h, 000h, 000h, 000h, 000h, 000h
   510 00014A99 38100000000000      <1>
   511 00014AA0 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   511 00014AA9 00000000000000      <1>
   512 00014AB0 0000183C3C3C181818- <1>     db  000h, 000h, 018h, 03ch, 03ch, 03ch, 018h, 018h, 018h, 000h, 018h, 018h, 000h, 000h, 000h, 000h
   512 00014AB9 00181800000000      <1>
   513 00014AC0 006666662400000000- <1>     db  000h, 066h, 066h, 066h, 024h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   513 00014AC9 00000000000000      <1>
   514 00014AD0 0000006C6CFE6C6C6C- <1>     db  000h, 000h, 000h, 06ch, 06ch, 0feh, 06ch, 06ch, 06ch, 0feh, 06ch, 06ch, 000h, 000h, 000h, 000h
   514 00014AD9 FE6C6C00000000      <1>
   515 00014AE0 18187CC6C2C07C0606- <1>     db  018h, 018h, 07ch, 0c6h, 0c2h, 0c0h, 07ch, 006h, 006h, 086h, 0c6h, 07ch, 018h, 018h, 000h, 000h
   515 00014AE9 86C67C18180000      <1>
   516 00014AF0 00000000C2C60C1830- <1>     db  000h, 000h, 000h, 000h, 0c2h, 0c6h, 00ch, 018h, 030h, 060h, 0c6h, 086h, 000h, 000h, 000h, 000h
   516 00014AF9 60C68600000000      <1>
   517 00014B00 0000386C6C3876DCCC- <1>     db  000h, 000h, 038h, 06ch, 06ch, 038h, 076h, 0dch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   517 00014B09 CCCC7600000000      <1>
   518 00014B10 003030306000000000- <1>     db  000h, 030h, 030h, 030h, 060h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   518 00014B19 00000000000000      <1>
   519 00014B20 00000C183030303030- <1>     db  000h, 000h, 00ch, 018h, 030h, 030h, 030h, 030h, 030h, 030h, 018h, 00ch, 000h, 000h, 000h, 000h
   519 00014B29 30180C00000000      <1>
   520 00014B30 000030180C0C0C0C0C- <1>     db  000h, 000h, 030h, 018h, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch, 018h, 030h, 000h, 000h, 000h, 000h
   520 00014B39 0C183000000000      <1>
   521 00014B40 0000000000663CFF3C- <1>     db  000h, 000h, 000h, 000h, 000h, 066h, 03ch, 0ffh, 03ch, 066h, 000h, 000h, 000h, 000h, 000h, 000h
   521 00014B49 66000000000000      <1>
   522 00014B50 000000000018187E18- <1>     db  000h, 000h, 000h, 000h, 000h, 018h, 018h, 07eh, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h
   522 00014B59 18000000000000      <1>
   523 00014B60 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 018h, 030h, 000h, 000h, 000h
   523 00014B69 18181830000000      <1>
   524 00014B70 00000000000000FE00- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   524 00014B79 00000000000000      <1>
   525 00014B80 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h
   525 00014B89 00181800000000      <1>
   526 00014B90 0000000002060C1830- <1>     db  000h, 000h, 000h, 000h, 002h, 006h, 00ch, 018h, 030h, 060h, 0c0h, 080h, 000h, 000h, 000h, 000h
   526 00014B99 60C08000000000      <1>
   527 00014BA0 00003C66C3C3DBDBC3- <1>     db  000h, 000h, 03ch, 066h, 0c3h, 0c3h, 0dbh, 0dbh, 0c3h, 0c3h, 066h, 03ch, 000h, 000h, 000h, 000h
   527 00014BA9 C3663C00000000      <1>
   528 00014BB0 000018387818181818- <1>     db  000h, 000h, 018h, 038h, 078h, 018h, 018h, 018h, 018h, 018h, 018h, 07eh, 000h, 000h, 000h, 000h
   528 00014BB9 18187E00000000      <1>
   529 00014BC0 00007CC6060C183060- <1>     db  000h, 000h, 07ch, 0c6h, 006h, 00ch, 018h, 030h, 060h, 0c0h, 0c6h, 0feh, 000h, 000h, 000h, 000h
   529 00014BC9 C0C6FE00000000      <1>
   530 00014BD0 00007CC606063C0606- <1>     db  000h, 000h, 07ch, 0c6h, 006h, 006h, 03ch, 006h, 006h, 006h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   530 00014BD9 06C67C00000000      <1>
   531 00014BE0 00000C1C3C6CCCFE0C- <1>     db  000h, 000h, 00ch, 01ch, 03ch, 06ch, 0cch, 0feh, 00ch, 00ch, 00ch, 01eh, 000h, 000h, 000h, 000h
   531 00014BE9 0C0C1E00000000      <1>
   532 00014BF0 0000FEC0C0C0FC0606- <1>     db  000h, 000h, 0feh, 0c0h, 0c0h, 0c0h, 0fch, 006h, 006h, 006h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   532 00014BF9 06C67C00000000      <1>
   533 00014C00 00003860C0C0FCC6C6- <1>     db  000h, 000h, 038h, 060h, 0c0h, 0c0h, 0fch, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   533 00014C09 C6C67C00000000      <1>
   534 00014C10 0000FEC606060C1830- <1>     db  000h, 000h, 0feh, 0c6h, 006h, 006h, 00ch, 018h, 030h, 030h, 030h, 030h, 000h, 000h, 000h, 000h
   534 00014C19 30303000000000      <1>
   535 00014C20 00007CC6C6C67CC6C6- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   535 00014C29 C6C67C00000000      <1>
   536 00014C30 00007CC6C6C67E0606- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 07eh, 006h, 006h, 006h, 00ch, 078h, 000h, 000h, 000h, 000h
   536 00014C39 060C7800000000      <1>
   537 00014C40 000000001818000000- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 000h
   537 00014C49 18180000000000      <1>
   538 00014C50 000000001818000000- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 018h, 018h, 030h, 000h, 000h, 000h, 000h
   538 00014C59 18183000000000      <1>
   539 00014C60 000000060C18306030- <1>     db  000h, 000h, 000h, 006h, 00ch, 018h, 030h, 060h, 030h, 018h, 00ch, 006h, 000h, 000h, 000h, 000h
   539 00014C69 180C0600000000      <1>
   540 00014C70 00000000007E00007E- <1>     db  000h, 000h, 000h, 000h, 000h, 07eh, 000h, 000h, 07eh, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   540 00014C79 00000000000000      <1>
   541 00014C80 0000006030180C060C- <1>     db  000h, 000h, 000h, 060h, 030h, 018h, 00ch, 006h, 00ch, 018h, 030h, 060h, 000h, 000h, 000h, 000h
   541 00014C89 18306000000000      <1>
   542 00014C90 00007CC6C60C181818- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 00ch, 018h, 018h, 018h, 000h, 018h, 018h, 000h, 000h, 000h, 000h
   542 00014C99 00181800000000      <1>
   543 00014CA0 0000007CC6C6DEDEDE- <1>     db  000h, 000h, 000h, 07ch, 0c6h, 0c6h, 0deh, 0deh, 0deh, 0dch, 0c0h, 07ch, 000h, 000h, 000h, 000h
   543 00014CA9 DCC07C00000000      <1>
   544 00014CB0 000010386CC6C6FEC6- <1>     db  000h, 000h, 010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   544 00014CB9 C6C6C600000000      <1>
   545 00014CC0 0000FC6666667C6666- <1>     db  000h, 000h, 0fch, 066h, 066h, 066h, 07ch, 066h, 066h, 066h, 066h, 0fch, 000h, 000h, 000h, 000h
   545 00014CC9 6666FC00000000      <1>
   546 00014CD0 00003C66C2C0C0C0C0- <1>     db  000h, 000h, 03ch, 066h, 0c2h, 0c0h, 0c0h, 0c0h, 0c0h, 0c2h, 066h, 03ch, 000h, 000h, 000h, 000h
   546 00014CD9 C2663C00000000      <1>
   547 00014CE0 0000F86C6666666666- <1>     db  000h, 000h, 0f8h, 06ch, 066h, 066h, 066h, 066h, 066h, 066h, 06ch, 0f8h, 000h, 000h, 000h, 000h
   547 00014CE9 666CF800000000      <1>
   548 00014CF0 0000FE666268786860- <1>     db  000h, 000h, 0feh, 066h, 062h, 068h, 078h, 068h, 060h, 062h, 066h, 0feh, 000h, 000h, 000h, 000h
   548 00014CF9 6266FE00000000      <1>
   549 00014D00 0000FE666268786860- <1>     db  000h, 000h, 0feh, 066h, 062h, 068h, 078h, 068h, 060h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h
   549 00014D09 6060F000000000      <1>
   550 00014D10 00003C66C2C0C0DEC6- <1>     db  000h, 000h, 03ch, 066h, 0c2h, 0c0h, 0c0h, 0deh, 0c6h, 0c6h, 066h, 03ah, 000h, 000h, 000h, 000h
   550 00014D19 C6663A00000000      <1>
   551 00014D20 0000C6C6C6C6FEC6C6- <1>     db  000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   551 00014D29 C6C6C600000000      <1>
   552 00014D30 00003C181818181818- <1>     db  000h, 000h, 03ch, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   552 00014D39 18183C00000000      <1>
   553 00014D40 00001E0C0C0C0C0CCC- <1>     db  000h, 000h, 01eh, 00ch, 00ch, 00ch, 00ch, 00ch, 0cch, 0cch, 0cch, 078h, 000h, 000h, 000h, 000h
   553 00014D49 CCCC7800000000      <1>
   554 00014D50 0000E666666C78786C- <1>     db  000h, 000h, 0e6h, 066h, 066h, 06ch, 078h, 078h, 06ch, 066h, 066h, 0e6h, 000h, 000h, 000h, 000h
   554 00014D59 6666E600000000      <1>
   555 00014D60 0000F0606060606060- <1>     db  000h, 000h, 0f0h, 060h, 060h, 060h, 060h, 060h, 060h, 062h, 066h, 0feh, 000h, 000h, 000h, 000h
   555 00014D69 6266FE00000000      <1>
   556 00014D70 0000C3E7FFFFDBC3C3- <1>     db  000h, 000h, 0c3h, 0e7h, 0ffh, 0ffh, 0dbh, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 000h, 000h, 000h, 000h
   556 00014D79 C3C3C300000000      <1>
   557 00014D80 0000C6E6F6FEDECEC6- <1>     db  000h, 000h, 0c6h, 0e6h, 0f6h, 0feh, 0deh, 0ceh, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   557 00014D89 C6C6C600000000      <1>
   558 00014D90 00007CC6C6C6C6C6C6- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   558 00014D99 C6C67C00000000      <1>
   559 00014DA0 0000FC6666667C6060- <1>     db  000h, 000h, 0fch, 066h, 066h, 066h, 07ch, 060h, 060h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h
   559 00014DA9 6060F000000000      <1>
   560 00014DB0 00007CC6C6C6C6C6C6- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0d6h, 0deh, 07ch, 00ch, 00eh, 000h, 000h
   560 00014DB9 D6DE7C0C0E0000      <1>
   561 00014DC0 0000FC6666667C6C66- <1>     db  000h, 000h, 0fch, 066h, 066h, 066h, 07ch, 06ch, 066h, 066h, 066h, 0e6h, 000h, 000h, 000h, 000h
   561 00014DC9 6666E600000000      <1>
   562 00014DD0 00007CC6C660380C06- <1>     db  000h, 000h, 07ch, 0c6h, 0c6h, 060h, 038h, 00ch, 006h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   562 00014DD9 C6C67C00000000      <1>
   563 00014DE0 0000FFDB9918181818- <1>     db  000h, 000h, 0ffh, 0dbh, 099h, 018h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   563 00014DE9 18183C00000000      <1>
   564 00014DF0 0000C6C6C6C6C6C6C6- <1>     db  000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   564 00014DF9 C6C67C00000000      <1>
   565 00014E00 0000C3C3C3C3C3C3C3- <1>     db  000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h, 000h, 000h, 000h, 000h
   565 00014E09 663C1800000000      <1>
   566 00014E10 0000C3C3C3C3C3DBDB- <1>     db  000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0dbh, 0dbh, 0ffh, 066h, 066h, 000h, 000h, 000h, 000h
   566 00014E19 FF666600000000      <1>
   567 00014E20 0000C3C3663C18183C- <1>     db  000h, 000h, 0c3h, 0c3h, 066h, 03ch, 018h, 018h, 03ch, 066h, 0c3h, 0c3h, 000h, 000h, 000h, 000h
   567 00014E29 66C3C300000000      <1>
   568 00014E30 0000C3C3C3663C1818- <1>     db  000h, 000h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   568 00014E39 18183C00000000      <1>
   569 00014E40 0000FFC3860C183060- <1>     db  000h, 000h, 0ffh, 0c3h, 086h, 00ch, 018h, 030h, 060h, 0c1h, 0c3h, 0ffh, 000h, 000h, 000h, 000h
   569 00014E49 C1C3FF00000000      <1>
   570 00014E50 00003C303030303030- <1>     db  000h, 000h, 03ch, 030h, 030h, 030h, 030h, 030h, 030h, 030h, 030h, 03ch, 000h, 000h, 000h, 000h
   570 00014E59 30303C00000000      <1>
   571 00014E60 00000080C0E070381C- <1>     db  000h, 000h, 000h, 080h, 0c0h, 0e0h, 070h, 038h, 01ch, 00eh, 006h, 002h, 000h, 000h, 000h, 000h
   571 00014E69 0E060200000000      <1>
   572 00014E70 00003C0C0C0C0C0C0C- <1>     db  000h, 000h, 03ch, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch, 00ch, 03ch, 000h, 000h, 000h, 000h
   572 00014E79 0C0C3C00000000      <1>
   573 00014E80 10386CC60000000000- <1>     db  010h, 038h, 06ch, 0c6h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   573 00014E89 00000000000000      <1>
   574 00014E90 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 000h
   574 00014E99 00000000FF0000      <1>
   575 00014EA0 303018000000000000- <1>     db  030h, 030h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   575 00014EA9 00000000000000      <1>
   576 00014EB0 0000000000780C7CCC- <1>     db  000h, 000h, 000h, 000h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   576 00014EB9 CCCC7600000000      <1>
   577 00014EC0 0000E06060786C6666- <1>     db  000h, 000h, 0e0h, 060h, 060h, 078h, 06ch, 066h, 066h, 066h, 066h, 07ch, 000h, 000h, 000h, 000h
   577 00014EC9 66667C00000000      <1>
   578 00014ED0 00000000007CC6C0C0- <1>     db  000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0c0h, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   578 00014ED9 C0C67C00000000      <1>
   579 00014EE0 00001C0C0C3C6CCCCC- <1>     db  000h, 000h, 01ch, 00ch, 00ch, 03ch, 06ch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   579 00014EE9 CCCC7600000000      <1>
   580 00014EF0 00000000007CC6FEC0- <1>     db  000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   580 00014EF9 C0C67C00000000      <1>
   581 00014F00 0000386C6460F06060- <1>     db  000h, 000h, 038h, 06ch, 064h, 060h, 0f0h, 060h, 060h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h
   581 00014F09 6060F000000000      <1>
   582 00014F10 000000000076CCCCCC- <1>     db  000h, 000h, 000h, 000h, 000h, 076h, 0cch, 0cch, 0cch, 0cch, 0cch, 07ch, 00ch, 0cch, 078h, 000h
   582 00014F19 CCCC7C0CCC7800      <1>
   583 00014F20 0000E060606C766666- <1>     db  000h, 000h, 0e0h, 060h, 060h, 06ch, 076h, 066h, 066h, 066h, 066h, 0e6h, 000h, 000h, 000h, 000h
   583 00014F29 6666E600000000      <1>
   584 00014F30 000018180038181818- <1>     db  000h, 000h, 018h, 018h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   584 00014F39 18183C00000000      <1>
   585 00014F40 00000606000E060606- <1>     db  000h, 000h, 006h, 006h, 000h, 00eh, 006h, 006h, 006h, 006h, 006h, 006h, 066h, 066h, 03ch, 000h
   585 00014F49 06060666663C00      <1>
   586 00014F50 0000E06060666C7878- <1>     db  000h, 000h, 0e0h, 060h, 060h, 066h, 06ch, 078h, 078h, 06ch, 066h, 0e6h, 000h, 000h, 000h, 000h
   586 00014F59 6C66E600000000      <1>
   587 00014F60 000038181818181818- <1>     db  000h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   587 00014F69 18183C00000000      <1>
   588 00014F70 0000000000E6FFDBDB- <1>     db  000h, 000h, 000h, 000h, 000h, 0e6h, 0ffh, 0dbh, 0dbh, 0dbh, 0dbh, 0dbh, 000h, 000h, 000h, 000h
   588 00014F79 DBDBDB00000000      <1>
   589 00014F80 0000000000DC666666- <1>     db  000h, 000h, 000h, 000h, 000h, 0dch, 066h, 066h, 066h, 066h, 066h, 066h, 000h, 000h, 000h, 000h
   589 00014F89 66666600000000      <1>
   590 00014F90 00000000007CC6C6C6- <1>     db  000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   590 00014F99 C6C67C00000000      <1>
   591 00014FA0 0000000000DC666666- <1>     db  000h, 000h, 000h, 000h, 000h, 0dch, 066h, 066h, 066h, 066h, 066h, 07ch, 060h, 060h, 0f0h, 000h
   591 00014FA9 66667C6060F000      <1>
   592 00014FB0 000000000076CCCCCC- <1>     db  000h, 000h, 000h, 000h, 000h, 076h, 0cch, 0cch, 0cch, 0cch, 0cch, 07ch, 00ch, 00ch, 01eh, 000h
   592 00014FB9 CCCC7C0C0C1E00      <1>
   593 00014FC0 0000000000DC766660- <1>     db  000h, 000h, 000h, 000h, 000h, 0dch, 076h, 066h, 060h, 060h, 060h, 0f0h, 000h, 000h, 000h, 000h
   593 00014FC9 6060F000000000      <1>
   594 00014FD0 00000000007CC66038- <1>     db  000h, 000h, 000h, 000h, 000h, 07ch, 0c6h, 060h, 038h, 00ch, 0c6h, 07ch, 000h, 000h, 000h, 000h
   594 00014FD9 0CC67C00000000      <1>
   595 00014FE0 0000103030FC303030- <1>     db  000h, 000h, 010h, 030h, 030h, 0fch, 030h, 030h, 030h, 030h, 036h, 01ch, 000h, 000h, 000h, 000h
   595 00014FE9 30361C00000000      <1>
   596 00014FF0 0000000000CCCCCCCC- <1>     db  000h, 000h, 000h, 000h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   596 00014FF9 CCCC7600000000      <1>
   597 00015000 0000000000C3C3C3C3- <1>     db  000h, 000h, 000h, 000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h, 000h, 000h, 000h, 000h
   597 00015009 663C1800000000      <1>
   598 00015010 0000000000C3C3C3DB- <1>     db  000h, 000h, 000h, 000h, 000h, 0c3h, 0c3h, 0c3h, 0dbh, 0dbh, 0ffh, 066h, 000h, 000h, 000h, 000h
   598 00015019 DBFF6600000000      <1>
   599 00015020 0000000000C3663C18- <1>     db  000h, 000h, 000h, 000h, 000h, 0c3h, 066h, 03ch, 018h, 03ch, 066h, 0c3h, 000h, 000h, 000h, 000h
   599 00015029 3C66C300000000      <1>
   600 00015030 0000000000C6C6C6C6- <1>     db  000h, 000h, 000h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07eh, 006h, 00ch, 0f8h, 000h
   600 00015039 C6C67E060CF800      <1>
   601 00015040 0000000000FECC1830- <1>     db  000h, 000h, 000h, 000h, 000h, 0feh, 0cch, 018h, 030h, 060h, 0c6h, 0feh, 000h, 000h, 000h, 000h
   601 00015049 60C6FE00000000      <1>
   602 00015050 00000E181818701818- <1>     db  000h, 000h, 00eh, 018h, 018h, 018h, 070h, 018h, 018h, 018h, 018h, 00eh, 000h, 000h, 000h, 000h
   602 00015059 18180E00000000      <1>
   603 00015060 000018181818001818- <1>     db  000h, 000h, 018h, 018h, 018h, 018h, 000h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   603 00015069 18181800000000      <1>
   604 00015070 0000701818180E1818- <1>     db  000h, 000h, 070h, 018h, 018h, 018h, 00eh, 018h, 018h, 018h, 018h, 070h, 000h, 000h, 000h, 000h
   604 00015079 18187000000000      <1>
   605 00015080 000076DC0000000000- <1>     db  000h, 000h, 076h, 0dch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   605 00015089 00000000000000      <1>
   606 00015090 0000000010386CC6C6- <1>     db  000h, 000h, 000h, 000h, 010h, 038h, 06ch, 0c6h, 0c6h, 0c6h, 0feh, 000h, 000h, 000h, 000h, 000h
   606 00015099 C6FE0000000000      <1>
   607 000150A0 00003C66C2C0C0C0C2- <1>     db  000h, 000h, 03ch, 066h, 0c2h, 0c0h, 0c0h, 0c0h, 0c2h, 066h, 03ch, 00ch, 006h, 07ch, 000h, 000h
   607 000150A9 663C0C067C0000      <1>
   608 000150B0 0000CC0000CCCCCCCC- <1>     db  000h, 000h, 0cch, 000h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   608 000150B9 CCCC7600000000      <1>
   609 000150C0 000C1830007CC6FEC0- <1>     db  000h, 00ch, 018h, 030h, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   609 000150C9 C0C67C00000000      <1>
   610 000150D0 0010386C00780C7CCC- <1>     db  000h, 010h, 038h, 06ch, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   610 000150D9 CCCC7600000000      <1>
   611 000150E0 0000CC0000780C7CCC- <1>     db  000h, 000h, 0cch, 000h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   611 000150E9 CCCC7600000000      <1>
   612 000150F0 0060301800780C7CCC- <1>     db  000h, 060h, 030h, 018h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   612 000150F9 CCCC7600000000      <1>
   613 00015100 00386C3800780C7CCC- <1>     db  000h, 038h, 06ch, 038h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   613 00015109 CCCC7600000000      <1>
   614 00015110 000000003C66606066- <1>     db  000h, 000h, 000h, 000h, 03ch, 066h, 060h, 060h, 066h, 03ch, 00ch, 006h, 03ch, 000h, 000h, 000h
   614 00015119 3C0C063C000000      <1>
   615 00015120 0010386C007CC6FEC0- <1>     db  000h, 010h, 038h, 06ch, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   615 00015129 C0C67C00000000      <1>
   616 00015130 0000C600007CC6FEC0- <1>     db  000h, 000h, 0c6h, 000h, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   616 00015139 C0C67C00000000      <1>
   617 00015140 00603018007CC6FEC0- <1>     db  000h, 060h, 030h, 018h, 000h, 07ch, 0c6h, 0feh, 0c0h, 0c0h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   617 00015149 C0C67C00000000      <1>
   618 00015150 000066000038181818- <1>     db  000h, 000h, 066h, 000h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   618 00015159 18183C00000000      <1>
   619 00015160 00183C660038181818- <1>     db  000h, 018h, 03ch, 066h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   619 00015169 18183C00000000      <1>
   620 00015170 006030180038181818- <1>     db  000h, 060h, 030h, 018h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   620 00015179 18183C00000000      <1>
   621 00015180 00C60010386CC6C6FE- <1>     db  000h, 0c6h, 000h, 010h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   621 00015189 C6C6C600000000      <1>
   622 00015190 386C3800386CC6C6FE- <1>     db  038h, 06ch, 038h, 000h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   622 00015199 C6C6C600000000      <1>
   623 000151A0 18306000FE66607C60- <1>     db  018h, 030h, 060h, 000h, 0feh, 066h, 060h, 07ch, 060h, 060h, 066h, 0feh, 000h, 000h, 000h, 000h
   623 000151A9 6066FE00000000      <1>
   624 000151B0 00000000006E3B1B7E- <1>     db  000h, 000h, 000h, 000h, 000h, 06eh, 03bh, 01bh, 07eh, 0d8h, 0dch, 077h, 000h, 000h, 000h, 000h
   624 000151B9 D8DC7700000000      <1>
   625 000151C0 00003E6CCCCCFECCCC- <1>     db  000h, 000h, 03eh, 06ch, 0cch, 0cch, 0feh, 0cch, 0cch, 0cch, 0cch, 0ceh, 000h, 000h, 000h, 000h
   625 000151C9 CCCCCE00000000      <1>
   626 000151D0 0010386C007CC6C6C6- <1>     db  000h, 010h, 038h, 06ch, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   626 000151D9 C6C67C00000000      <1>
   627 000151E0 0000C600007CC6C6C6- <1>     db  000h, 000h, 0c6h, 000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   627 000151E9 C6C67C00000000      <1>
   628 000151F0 00603018007CC6C6C6- <1>     db  000h, 060h, 030h, 018h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   628 000151F9 C6C67C00000000      <1>
   629 00015200 003078CC00CCCCCCCC- <1>     db  000h, 030h, 078h, 0cch, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   629 00015209 CCCC7600000000      <1>
   630 00015210 0060301800CCCCCCCC- <1>     db  000h, 060h, 030h, 018h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   630 00015219 CCCC7600000000      <1>
   631 00015220 0000C60000C6C6C6C6- <1>     db  000h, 000h, 0c6h, 000h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07eh, 006h, 00ch, 078h, 000h
   631 00015229 C6C67E060C7800      <1>
   632 00015230 00C6007CC6C6C6C6C6- <1>     db  000h, 0c6h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   632 00015239 C6C67C00000000      <1>
   633 00015240 00C600C6C6C6C6C6C6- <1>     db  000h, 0c6h, 000h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   633 00015249 C6C67C00000000      <1>
   634 00015250 0018187EC3C0C0C0C3- <1>     db  000h, 018h, 018h, 07eh, 0c3h, 0c0h, 0c0h, 0c0h, 0c3h, 07eh, 018h, 018h, 000h, 000h, 000h, 000h
   634 00015259 7E181800000000      <1>
   635 00015260 00386C6460F0606060- <1>     db  000h, 038h, 06ch, 064h, 060h, 0f0h, 060h, 060h, 060h, 060h, 0e6h, 0fch, 000h, 000h, 000h, 000h
   635 00015269 60E6FC00000000      <1>
   636 00015270 0000C3663C18FF18FF- <1>     db  000h, 000h, 0c3h, 066h, 03ch, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   636 00015279 18181800000000      <1>
   637 00015280 00FC66667C62666F66- <1>     db  000h, 0fch, 066h, 066h, 07ch, 062h, 066h, 06fh, 066h, 066h, 066h, 0f3h, 000h, 000h, 000h, 000h
   637 00015289 6666F300000000      <1>
   638 00015290 000E1B1818187E1818- <1>     db  000h, 00eh, 01bh, 018h, 018h, 018h, 07eh, 018h, 018h, 018h, 018h, 018h, 0d8h, 070h, 000h, 000h
   638 00015299 181818D8700000      <1>
   639 000152A0 0018306000780C7CCC- <1>     db  000h, 018h, 030h, 060h, 000h, 078h, 00ch, 07ch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   639 000152A9 CCCC7600000000      <1>
   640 000152B0 000C18300038181818- <1>     db  000h, 00ch, 018h, 030h, 000h, 038h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h
   640 000152B9 18183C00000000      <1>
   641 000152C0 00183060007CC6C6C6- <1>     db  000h, 018h, 030h, 060h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   641 000152C9 C6C67C00000000      <1>
   642 000152D0 0018306000CCCCCCCC- <1>     db  000h, 018h, 030h, 060h, 000h, 0cch, 0cch, 0cch, 0cch, 0cch, 0cch, 076h, 000h, 000h, 000h, 000h
   642 000152D9 CCCC7600000000      <1>
   643 000152E0 000076DC00DC666666- <1>     db  000h, 000h, 076h, 0dch, 000h, 0dch, 066h, 066h, 066h, 066h, 066h, 066h, 000h, 000h, 000h, 000h
   643 000152E9 66666600000000      <1>
   644 000152F0 76DC00C6E6F6FEDECE- <1>     db  076h, 0dch, 000h, 0c6h, 0e6h, 0f6h, 0feh, 0deh, 0ceh, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   644 000152F9 C6C6C600000000      <1>
   645 00015300 003C6C6C3E007E0000- <1>     db  000h, 03ch, 06ch, 06ch, 03eh, 000h, 07eh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   645 00015309 00000000000000      <1>
   646 00015310 00386C6C38007C0000- <1>     db  000h, 038h, 06ch, 06ch, 038h, 000h, 07ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   646 00015319 00000000000000      <1>
   647 00015320 0000303000303060C0- <1>     db  000h, 000h, 030h, 030h, 000h, 030h, 030h, 060h, 0c0h, 0c6h, 0c6h, 07ch, 000h, 000h, 000h, 000h
   647 00015329 C6C67C00000000      <1>
   648 00015330 000000000000FEC0C0- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 0feh, 0c0h, 0c0h, 0c0h, 0c0h, 000h, 000h, 000h, 000h, 000h
   648 00015339 C0C00000000000      <1>
   649 00015340 000000000000FE0606- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 0feh, 006h, 006h, 006h, 006h, 000h, 000h, 000h, 000h, 000h
   649 00015349 06060000000000      <1>
   650 00015350 00C0C0C2C6CC183060- <1>     db  000h, 0c0h, 0c0h, 0c2h, 0c6h, 0cch, 018h, 030h, 060h, 0ceh, 09bh, 006h, 00ch, 01fh, 000h, 000h
   650 00015359 CE9B060C1F0000      <1>
   651 00015360 00C0C0C2C6CC183066- <1>     db  000h, 0c0h, 0c0h, 0c2h, 0c6h, 0cch, 018h, 030h, 066h, 0ceh, 096h, 03eh, 006h, 006h, 000h, 000h
   651 00015369 CE963E06060000      <1>
   652 00015370 00001818001818183C- <1>     db  000h, 000h, 018h, 018h, 000h, 018h, 018h, 018h, 03ch, 03ch, 03ch, 018h, 000h, 000h, 000h, 000h
   652 00015379 3C3C1800000000      <1>
   653 00015380 0000000000366CD86C- <1>     db  000h, 000h, 000h, 000h, 000h, 036h, 06ch, 0d8h, 06ch, 036h, 000h, 000h, 000h, 000h, 000h, 000h
   653 00015389 36000000000000      <1>
   654 00015390 0000000000D86C366C- <1>     db  000h, 000h, 000h, 000h, 000h, 0d8h, 06ch, 036h, 06ch, 0d8h, 000h, 000h, 000h, 000h, 000h, 000h
   654 00015399 D8000000000000      <1>
   655 000153A0 114411441144114411- <1>     db  011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h, 011h, 044h
   655 000153A9 44114411441144      <1>
   656 000153B0 55AA55AA55AA55AA55- <1>     db  055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah, 055h, 0aah
   656 000153B9 AA55AA55AA55AA      <1>
   657 000153C0 DD77DD77DD77DD77DD- <1>     db  0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h, 0ddh, 077h
   657 000153C9 77DD77DD77DD77      <1>
   658 000153D0 181818181818181818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   658 000153D9 18181818181818      <1>
   659 000153E0 18181818181818F818- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   659 000153E9 18181818181818      <1>
   660 000153F0 1818181818F818F818- <1>     db  018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   660 000153F9 18181818181818      <1>
   661 00015400 36363636363636F636- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 0f6h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   661 00015409 36363636363636      <1>
   662 00015410 00000000000000FE36- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0feh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   662 00015419 36363636363636      <1>
   663 00015420 0000000000F818F818- <1>     db  000h, 000h, 000h, 000h, 000h, 0f8h, 018h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   663 00015429 18181818181818      <1>
   664 00015430 3636363636F606F636- <1>     db  036h, 036h, 036h, 036h, 036h, 0f6h, 006h, 0f6h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   664 00015439 36363636363636      <1>
   665 00015440 363636363636363636- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   665 00015449 36363636363636      <1>
   666 00015450 0000000000FE06F636- <1>     db  000h, 000h, 000h, 000h, 000h, 0feh, 006h, 0f6h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   666 00015459 36363636363636      <1>
   667 00015460 3636363636F606FE00- <1>     db  036h, 036h, 036h, 036h, 036h, 0f6h, 006h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   667 00015469 00000000000000      <1>
   668 00015470 36363636363636FE00- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 0feh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   668 00015479 00000000000000      <1>
   669 00015480 1818181818F818F800- <1>     db  018h, 018h, 018h, 018h, 018h, 0f8h, 018h, 0f8h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   669 00015489 00000000000000      <1>
   670 00015490 00000000000000F818- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0f8h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   670 00015499 18181818181818      <1>
   671 000154A0 181818181818181F00- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 01fh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   671 000154A9 00000000000000      <1>
   672 000154B0 18181818181818FF00- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   672 000154B9 00000000000000      <1>
   673 000154C0 00000000000000FF18- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   673 000154C9 18181818181818      <1>
   674 000154D0 181818181818181F18- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   674 000154D9 18181818181818      <1>
   675 000154E0 00000000000000FF00- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   675 000154E9 00000000000000      <1>
   676 000154F0 18181818181818FF18- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   676 000154F9 18181818181818      <1>
   677 00015500 18181818181F181F18- <1>     db  018h, 018h, 018h, 018h, 018h, 01fh, 018h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   677 00015509 18181818181818      <1>
   678 00015510 363636363636363736- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 037h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   678 00015519 36363636363636      <1>
   679 00015520 363636363637303F00- <1>     db  036h, 036h, 036h, 036h, 036h, 037h, 030h, 03fh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   679 00015529 00000000000000      <1>
   680 00015530 00000000003F303736- <1>     db  000h, 000h, 000h, 000h, 000h, 03fh, 030h, 037h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   680 00015539 36363636363636      <1>
   681 00015540 3636363636F700FF00- <1>     db  036h, 036h, 036h, 036h, 036h, 0f7h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   681 00015549 00000000000000      <1>
   682 00015550 0000000000FF00F736- <1>     db  000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0f7h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   682 00015559 36363636363636      <1>
   683 00015560 363636363637303736- <1>     db  036h, 036h, 036h, 036h, 036h, 037h, 030h, 037h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   683 00015569 36363636363636      <1>
   684 00015570 0000000000FF00FF00- <1>     db  000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   684 00015579 00000000000000      <1>
   685 00015580 3636363636F700F736- <1>     db  036h, 036h, 036h, 036h, 036h, 0f7h, 000h, 0f7h, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   685 00015589 36363636363636      <1>
   686 00015590 1818181818FF00FF00- <1>     db  018h, 018h, 018h, 018h, 018h, 0ffh, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   686 00015599 00000000000000      <1>
   687 000155A0 36363636363636FF00- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   687 000155A9 00000000000000      <1>
   688 000155B0 0000000000FF00FF18- <1>     db  000h, 000h, 000h, 000h, 000h, 0ffh, 000h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   688 000155B9 18181818181818      <1>
   689 000155C0 00000000000000FF36- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   689 000155C9 36363636363636      <1>
   690 000155D0 363636363636363F00- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 03fh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   690 000155D9 00000000000000      <1>
   691 000155E0 18181818181F181F00- <1>     db  018h, 018h, 018h, 018h, 018h, 01fh, 018h, 01fh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   691 000155E9 00000000000000      <1>
   692 000155F0 00000000001F181F18- <1>     db  000h, 000h, 000h, 000h, 000h, 01fh, 018h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   692 000155F9 18181818181818      <1>
   693 00015600 000000000000003F36- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 03fh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   693 00015609 36363636363636      <1>
   694 00015610 36363636363636FF36- <1>     db  036h, 036h, 036h, 036h, 036h, 036h, 036h, 0ffh, 036h, 036h, 036h, 036h, 036h, 036h, 036h, 036h
   694 00015619 36363636363636      <1>
   695 00015620 1818181818FF18FF18- <1>     db  018h, 018h, 018h, 018h, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   695 00015629 18181818181818      <1>
   696 00015630 18181818181818F800- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 0f8h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   696 00015639 00000000000000      <1>
   697 00015640 000000000000001F18- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 01fh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   697 00015649 18181818181818      <1>
   698 00015650 FFFFFFFFFFFFFFFFFF- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   698 00015659 FFFFFFFFFFFFFF      <1>
   699 00015660 00000000000000FFFF- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh
   699 00015669 FFFFFFFFFFFFFF      <1>
   700 00015670 F0F0F0F0F0F0F0F0F0- <1>     db  0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h, 0f0h
   700 00015679 F0F0F0F0F0F0F0      <1>
   701 00015680 0F0F0F0F0F0F0F0F0F- <1>     db  00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh, 00fh
   701 00015689 0F0F0F0F0F0F0F      <1>
   702 00015690 FFFFFFFFFFFFFF0000- <1>     db  0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   702 00015699 00000000000000      <1>
   703 000156A0 000000000076DCD8D8- <1>     db  000h, 000h, 000h, 000h, 000h, 076h, 0dch, 0d8h, 0d8h, 0d8h, 0dch, 076h, 000h, 000h, 000h, 000h
   703 000156A9 D8DC7600000000      <1>
   704 000156B0 000078CCCCCCD8CCC6- <1>     db  000h, 000h, 078h, 0cch, 0cch, 0cch, 0d8h, 0cch, 0c6h, 0c6h, 0c6h, 0cch, 000h, 000h, 000h, 000h
   704 000156B9 C6C6CC00000000      <1>
   705 000156C0 0000FEC6C6C0C0C0C0- <1>     db  000h, 000h, 0feh, 0c6h, 0c6h, 0c0h, 0c0h, 0c0h, 0c0h, 0c0h, 0c0h, 0c0h, 000h, 000h, 000h, 000h
   705 000156C9 C0C0C000000000      <1>
   706 000156D0 00000000FE6C6C6C6C- <1>     db  000h, 000h, 000h, 000h, 0feh, 06ch, 06ch, 06ch, 06ch, 06ch, 06ch, 06ch, 000h, 000h, 000h, 000h
   706 000156D9 6C6C6C00000000      <1>
   707 000156E0 000000FEC660301830- <1>     db  000h, 000h, 000h, 0feh, 0c6h, 060h, 030h, 018h, 030h, 060h, 0c6h, 0feh, 000h, 000h, 000h, 000h
   707 000156E9 60C6FE00000000      <1>
   708 000156F0 00000000007ED8D8D8- <1>     db  000h, 000h, 000h, 000h, 000h, 07eh, 0d8h, 0d8h, 0d8h, 0d8h, 0d8h, 070h, 000h, 000h, 000h, 000h
   708 000156F9 D8D87000000000      <1>
   709 00015700 000000006666666666- <1>     db  000h, 000h, 000h, 000h, 066h, 066h, 066h, 066h, 066h, 07ch, 060h, 060h, 0c0h, 000h, 000h, 000h
   709 00015709 7C6060C0000000      <1>
   710 00015710 0000000076DC181818- <1>     db  000h, 000h, 000h, 000h, 076h, 0dch, 018h, 018h, 018h, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   710 00015719 18181800000000      <1>
   711 00015720 0000007E183C666666- <1>     db  000h, 000h, 000h, 07eh, 018h, 03ch, 066h, 066h, 066h, 03ch, 018h, 07eh, 000h, 000h, 000h, 000h
   711 00015729 3C187E00000000      <1>
   712 00015730 000000386CC6C6FEC6- <1>     db  000h, 000h, 000h, 038h, 06ch, 0c6h, 0c6h, 0feh, 0c6h, 0c6h, 06ch, 038h, 000h, 000h, 000h, 000h
   712 00015739 C66C3800000000      <1>
   713 00015740 0000386CC6C6C66C6C- <1>     db  000h, 000h, 038h, 06ch, 0c6h, 0c6h, 0c6h, 06ch, 06ch, 06ch, 06ch, 0eeh, 000h, 000h, 000h, 000h
   713 00015749 6C6CEE00000000      <1>
   714 00015750 00001E30180C3E6666- <1>     db  000h, 000h, 01eh, 030h, 018h, 00ch, 03eh, 066h, 066h, 066h, 066h, 03ch, 000h, 000h, 000h, 000h
   714 00015759 66663C00000000      <1>
   715 00015760 00000000007EDBDBDB- <1>     db  000h, 000h, 000h, 000h, 000h, 07eh, 0dbh, 0dbh, 0dbh, 07eh, 000h, 000h, 000h, 000h, 000h, 000h
   715 00015769 7E000000000000      <1>
   716 00015770 00000003067EDBDBF3- <1>     db  000h, 000h, 000h, 003h, 006h, 07eh, 0dbh, 0dbh, 0f3h, 07eh, 060h, 0c0h, 000h, 000h, 000h, 000h
   716 00015779 7E60C000000000      <1>
   717 00015780 00001C3060607C6060- <1>     db  000h, 000h, 01ch, 030h, 060h, 060h, 07ch, 060h, 060h, 060h, 030h, 01ch, 000h, 000h, 000h, 000h
   717 00015789 60301C00000000      <1>
   718 00015790 0000007CC6C6C6C6C6- <1>     db  000h, 000h, 000h, 07ch, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 0c6h, 000h, 000h, 000h, 000h
   718 00015799 C6C6C600000000      <1>
   719 000157A0 00000000FE0000FE00- <1>     db  000h, 000h, 000h, 000h, 0feh, 000h, 000h, 0feh, 000h, 000h, 0feh, 000h, 000h, 000h, 000h, 000h
   719 000157A9 00FE0000000000      <1>
   720 000157B0 0000000018187E1818- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 07eh, 018h, 018h, 000h, 000h, 0ffh, 000h, 000h, 000h, 000h
   720 000157B9 0000FF00000000      <1>
   721 000157C0 00000030180C060C18- <1>     db  000h, 000h, 000h, 030h, 018h, 00ch, 006h, 00ch, 018h, 030h, 000h, 07eh, 000h, 000h, 000h, 000h
   721 000157C9 30007E00000000      <1>
   722 000157D0 0000000C1830603018- <1>     db  000h, 000h, 000h, 00ch, 018h, 030h, 060h, 030h, 018h, 00ch, 000h, 07eh, 000h, 000h, 000h, 000h
   722 000157D9 0C007E00000000      <1>
   723 000157E0 00000E1B1B18181818- <1>     db  000h, 000h, 00eh, 01bh, 01bh, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h
   723 000157E9 18181818181818      <1>
   724 000157F0 1818181818181818D8- <1>     db  018h, 018h, 018h, 018h, 018h, 018h, 018h, 018h, 0d8h, 0d8h, 0d8h, 070h, 000h, 000h, 000h, 000h
   724 000157F9 D8D87000000000      <1>
   725 00015800 000000001818007E00- <1>     db  000h, 000h, 000h, 000h, 018h, 018h, 000h, 07eh, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 000h
   725 00015809 18180000000000      <1>
   726 00015810 000000000076DC0076- <1>     db  000h, 000h, 000h, 000h, 000h, 076h, 0dch, 000h, 076h, 0dch, 000h, 000h, 000h, 000h, 000h, 000h
   726 00015819 DC000000000000      <1>
   727 00015820 00386C6C3800000000- <1>     db  000h, 038h, 06ch, 06ch, 038h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   727 00015829 00000000000000      <1>
   728 00015830 000000000000001818- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   728 00015839 00000000000000      <1>
   729 00015840 000000000000000018- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 018h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   729 00015849 00000000000000      <1>
   730 00015850 000F0C0C0C0C0CEC6C- <1>     db  000h, 00fh, 00ch, 00ch, 00ch, 00ch, 00ch, 0ech, 06ch, 06ch, 03ch, 01ch, 000h, 000h, 000h, 000h
   730 00015859 6C3C1C00000000      <1>
   731 00015860 00D86C6C6C6C6C0000- <1>     db  000h, 0d8h, 06ch, 06ch, 06ch, 06ch, 06ch, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   731 00015869 00000000000000      <1>
   732 00015870 0070D83060C8F80000- <1>     db  000h, 070h, 0d8h, 030h, 060h, 0c8h, 0f8h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   732 00015879 00000000000000      <1>
   733 00015880 000000007C7C7C7C7C- <1>     db  000h, 000h, 000h, 000h, 07ch, 07ch, 07ch, 07ch, 07ch, 07ch, 07ch, 000h, 000h, 000h, 000h, 000h
   733 00015889 7C7C0000000000      <1>
   734 00015890 000000000000000000- <1>     db  000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h
   734 00015899 00000000000000      <1>
   735                              <1> vgafont14alt:
   736 000158A0 1D000000002466FF66- <1>     db  01dh, 000h, 000h, 000h, 000h, 024h, 066h, 0ffh, 066h, 024h, 000h, 000h, 000h, 000h, 000h, 022h
   736 000158A9 24000000000022      <1>
   737 000158B0 006363632200000000- <1>     db  000h, 063h, 063h, 063h, 022h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 02bh, 000h
   737 000158B9 00000000002B00      <1>
   738 000158C0 0000181818FF181818- <1>     db  000h, 000h, 018h, 018h, 018h, 0ffh, 018h, 018h, 018h, 000h, 000h, 000h, 000h, 02dh, 000h, 000h
   738 000158C9 000000002D0000      <1>
   739 000158D0 00000000FF00000000- <1>     db  000h, 000h, 000h, 000h, 0ffh, 000h, 000h, 000h, 000h, 000h, 000h, 000h, 04dh, 000h, 000h, 0c3h
   739 000158D9 0000004D0000C3      <1>
   740 000158E0 E7FFDBC3C3C3C3C300- <1>     db  0e7h, 0ffh, 0dbh, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 000h, 000h, 000h, 054h, 000h, 000h, 0ffh, 0dbh
   740 000158E9 0000540000FFDB      <1>
   741 000158F0 9918181818183C0000- <1>     db  099h, 018h, 018h, 018h, 018h, 018h, 03ch, 000h, 000h, 000h, 056h, 000h, 000h, 0c3h, 0c3h, 0c3h
   741 000158F9 00560000C3C3C3      <1>
   742 00015900 C3C3C3663C18000000- <1>     db  0c3h, 0c3h, 0c3h, 066h, 03ch, 018h, 000h, 000h, 000h, 057h, 000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h
   742 00015909 570000C3C3C3C3      <1>
   743 00015910 DBDBFF666600000058- <1>     db  0dbh, 0dbh, 0ffh, 066h, 066h, 000h, 000h, 000h, 058h, 000h, 000h, 0c3h, 0c3h, 066h, 03ch, 018h
   743 00015919 0000C3C3663C18      <1>
   744 00015920 3C66C3C30000005900- <1>     db  03ch, 066h, 0c3h, 0c3h, 000h, 000h, 000h, 059h, 000h, 000h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h
   744 00015929 00C3C3C3663C18      <1>
   745 00015930 18183C0000005A0000- <1>     db  018h, 018h, 03ch, 000h, 000h, 000h, 05ah, 000h, 000h, 0ffh, 0c3h, 086h, 00ch, 018h, 030h, 061h
   745 00015939 FFC3860C183061      <1>
   746 00015940 C3FF0000006D000000- <1>     db  0c3h, 0ffh, 000h, 000h, 000h, 06dh, 000h, 000h, 000h, 000h, 000h, 0e6h, 0ffh, 0dbh, 0dbh, 0dbh
   746 00015949 0000E6FFDBDBDB      <1>
   747 00015950 DB0000007600000000- <1>     db  0dbh, 000h, 000h, 000h, 076h, 000h, 000h, 000h, 000h, 000h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h
   747 00015959 00C3C3C3663C18      <1>
   748 00015960 000000770000000000- <1>     db  000h, 000h, 000h, 077h, 000h, 000h, 000h, 000h, 000h, 0c3h, 0c3h, 0dbh, 0dbh, 0ffh, 066h, 000h
   748 00015969 C3C3DBDBFF6600      <1>
   749 00015970 000091000000006E3B- <1>     db  000h, 000h, 091h, 000h, 000h, 000h, 000h, 06eh, 03bh, 01bh, 07eh, 0d8h, 0dch, 077h, 000h, 000h
   749 00015979 1B7ED8DC770000      <1>
   750 00015980 009B0018187EC3C0C0- <1>     db  000h, 09bh, 000h, 018h, 018h, 07eh, 0c3h, 0c0h, 0c0h, 0c3h, 07eh, 018h, 018h, 000h, 000h, 000h
   750 00015989 C37E1818000000      <1>
   751 00015990 9D0000C3663C18FF18- <1>     db  09dh, 000h, 000h, 0c3h, 066h, 03ch, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 000h, 000h, 000h, 09eh
   751 00015999 FF18180000009E      <1>
   752 000159A0 00FC66667C62666F66- <1>     db  000h, 0fch, 066h, 066h, 07ch, 062h, 066h, 06fh, 066h, 066h, 0f3h, 000h, 000h, 000h, 0f1h, 000h
   752 000159A9 66F3000000F100      <1>
   753 000159B0 00181818FF18181800- <1>     db  000h, 018h, 018h, 018h, 0ffh, 018h, 018h, 018h, 000h, 0ffh, 000h, 000h, 000h, 0f6h, 000h, 000h
   753 000159B9 FF000000F60000      <1>
   754 000159C0 18180000FF00001818- <1>     db  018h, 018h, 000h, 000h, 0ffh, 000h, 000h, 018h, 018h, 000h, 000h, 000h, 000h
   754 000159C9 00000000            <1>
   755                              <1> vgafont16alt:
   756 000159CD 1D00000000002466FF- <1>     db  01dh, 000h, 000h, 000h, 000h, 000h, 024h, 066h, 0ffh, 066h, 024h, 000h, 000h, 000h, 000h, 000h
   756 000159D6 66240000000000      <1>
   757 000159DD 003000003C66C3C3DB- <1>     db  000h, 030h, 000h, 000h, 03ch, 066h, 0c3h, 0c3h, 0dbh, 0dbh, 0c3h, 0c3h, 066h, 03ch, 000h, 000h
   757 000159E6 DBC3C3663C0000      <1>
   758 000159ED 00004D0000C3E7FFFF- <1>     db  000h, 000h, 04dh, 000h, 000h, 0c3h, 0e7h, 0ffh, 0ffh, 0dbh, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 000h
   758 000159F6 DBC3C3C3C3C300      <1>
   759 000159FD 000000540000FFDB99- <1>     db  000h, 000h, 000h, 054h, 000h, 000h, 0ffh, 0dbh, 099h, 018h, 018h, 018h, 018h, 018h, 018h, 03ch
   759 00015A06 1818181818183C      <1>
   760 00015A0D 00000000560000C3C3- <1>     db  000h, 000h, 000h, 000h, 056h, 000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 066h, 03ch
   760 00015A16 C3C3C3C3C3663C      <1>
   761 00015A1D 1800000000570000C3- <1>     db  018h, 000h, 000h, 000h, 000h, 057h, 000h, 000h, 0c3h, 0c3h, 0c3h, 0c3h, 0c3h, 0dbh, 0dbh, 0ffh
   761 00015A26 C3C3C3C3DBDBFF      <1>
   762 00015A2D 666600000000580000- <1>     db  066h, 066h, 000h, 000h, 000h, 000h, 058h, 000h, 000h, 0c3h, 0c3h, 066h, 03ch, 018h, 018h, 03ch
   762 00015A36 C3C3663C18183C      <1>
   763 00015A3D 66C3C3000000005900- <1>     db  066h, 0c3h, 0c3h, 000h, 000h, 000h, 000h, 059h, 000h, 000h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h
   763 00015A46 00C3C3C3663C18      <1>
   764 00015A4D 1818183C000000005A- <1>     db  018h, 018h, 018h, 03ch, 000h, 000h, 000h, 000h, 05ah, 000h, 000h, 0ffh, 0c3h, 086h, 00ch, 018h
   764 00015A56 0000FFC3860C18      <1>
   765 00015A5D 3060C1C3FF00000000- <1>     db  030h, 060h, 0c1h, 0c3h, 0ffh, 000h, 000h, 000h, 000h, 06dh, 000h, 000h, 000h, 000h, 000h, 0e6h
   765 00015A66 6D0000000000E6      <1>
   766 00015A6D FFDBDBDBDBDB000000- <1>     db  0ffh, 0dbh, 0dbh, 0dbh, 0dbh, 0dbh, 000h, 000h, 000h, 000h, 076h, 000h, 000h, 000h, 000h, 000h
   766 00015A76 00760000000000      <1>
   767 00015A7D C3C3C3C3663C180000- <1>     db  0c3h, 0c3h, 0c3h, 0c3h, 066h, 03ch, 018h, 000h, 000h, 000h, 000h, 077h, 000h, 000h, 000h, 000h
   767 00015A86 00007700000000      <1>
   768 00015A8D 00C3C3C3DBDBFF6600- <1>     db  000h, 0c3h, 0c3h, 0c3h, 0dbh, 0dbh, 0ffh, 066h, 000h, 000h, 000h, 000h, 078h, 000h, 000h, 000h
   768 00015A96 00000078000000      <1>
   769 00015A9D 0000C3663C183C66C3- <1>     db  000h, 000h, 0c3h, 066h, 03ch, 018h, 03ch, 066h, 0c3h, 000h, 000h, 000h, 000h, 091h, 000h, 000h
   769 00015AA6 00000000910000      <1>
   770 00015AAD 0000006E3B1B7ED8DC- <1>     db  000h, 000h, 000h, 06eh, 03bh, 01bh, 07eh, 0d8h, 0dch, 077h, 000h, 000h, 000h, 000h, 09bh, 000h
   770 00015AB6 77000000009B00      <1>
   771 00015ABD 18187EC3C0C0C0C37E- <1>     db  018h, 018h, 07eh, 0c3h, 0c0h, 0c0h, 0c0h, 0c3h, 07eh, 018h, 018h, 000h, 000h, 000h, 000h, 09dh
   771 00015AC6 1818000000009D      <1>
   772 00015ACD 0000C3663C18FF18FF- <1>     db  000h, 000h, 0c3h, 066h, 03ch, 018h, 0ffh, 018h, 0ffh, 018h, 018h, 018h, 000h, 000h, 000h, 000h
   772 00015AD6 18181800000000      <1>
   773 00015ADD 9E00FC66667C62666F- <1>     db  09eh, 000h, 0fch, 066h, 066h, 07ch, 062h, 066h, 06fh, 066h, 066h, 066h, 0f3h, 000h, 000h, 000h
   773 00015AE6 666666F3000000      <1>
   774 00015AED 00AB00C0C0C2C6CC18- <1>     db  000h, 0abh, 000h, 0c0h, 0c0h, 0c2h, 0c6h, 0cch, 018h, 030h, 060h, 0ceh, 09bh, 006h, 00ch, 01fh
   774 00015AF6 3060CE9B060C1F      <1>
   775 00015AFD 0000AC00C0C0C2C6CC- <1>     db  000h, 000h, 0ach, 000h, 0c0h, 0c0h, 0c2h, 0c6h, 0cch, 018h, 030h, 066h, 0ceh, 096h, 03eh, 006h
   775 00015B06 183066CE963E06      <1>
   776 00015B0D 06000000            <1>     db  006h, 000h, 000h, 000h
  3202                                  
  3203                                  ; 20/11/2020
  3204                                  vbe2_bochs_vbios:
  3205                                  ;	db "BOCHS/QEMU"
  3206 00015B11 424F4348532F51454D-     	db "BOCHS/QEMU/VIRTUALBOX"  ; 26/11/2020
  3206 00015B1A 552F5649525455414C-
  3206 00015B23 424F58             
  3207                                  ;vbe_vnumber equ vbe2_bochs_vbios + 28 ; "3" or "2"
  3208                                  ; 26/11/2020
  3209                                  vbe_vnumber equ vbe2_bochs_vbios + 30 ; "3" or "2"
  3210                                  ; 15/11/2020
  3211                                  vesa_vbe3_bios_msg:
  3212                                  	;db " VESA VBE version 3 Video BIOS ..."
  3213 00015B26 205645534120564245-     	db " VESA VBE3 Video BIOS ..." ; 26/11/2020
  3213 00015B2F 3320566964656F2042-
  3213 00015B38 494F53202E2E2E     
  3214 00015B3F 0D0A0D0A00              	db 0Dh, 0Ah, 0Dh, 0Ah, 0
  3215                                  
  3216                                  align 2
  3217                                  
  3218                                  ; EPOCH Variables
  3219                                  ; 13/04/2015 - Retro UNIX 386 v1 Beginning
  3220                                  ; 09/04/2013 epoch variables
  3221                                  ; Retro UNIX 8086 v1 Prototype: UNIXCOPY.ASM, 10/03/2013
  3222                                  ;
  3223 00015B44 B207                    year: 	dw 1970
  3224 00015B46 0100                    month: 	dw 1
  3225 00015B48 0100                    day: 	dw 1
  3226 00015B4A 0000                    hour: 	dw 0
  3227 00015B4C 0000                    minute: dw 0
  3228 00015B4E 0000                    second: dw 0
  3229                                  
  3230                                  DMonth:
  3231 00015B50 0000                    	dw 0
  3232 00015B52 1F00                    	dw 31
  3233 00015B54 3B00                    	dw 59
  3234 00015B56 5A00                    	dw 90
  3235 00015B58 7800                    	dw 120
  3236 00015B5A 9700                    	dw 151
  3237 00015B5C B500                    	dw 181
  3238 00015B5E D400                    	dw 212
  3239 00015B60 F300                    	dw 243
  3240 00015B62 1101                    	dw 273
  3241 00015B64 3001                    	dw 304
  3242 00015B66 4E01                    	dw 334
  3243                                  
  3244                                  ; 15/11/2020
  3245 00015B68 00                      db	0
  3246                                  kernel_version_msg: ; 20/11/2020
  3247 00015B69 5452444F5320283338-     db	"TRDOS (386) Kernel v2.0.3 by Erdogan Tan"
  3247 00015B72 3629204B65726E656C-
  3247 00015B7B 2076322E302E332062-
  3247 00015B84 79204572646F67616E-
  3247 00015B8D 2054616E           
  3248 00015B91 00                      db	0
  3249                                  
  3250                                  ; 20/02/2017
  3251                                  KERNELFSIZE  equ $  ; 04/07/2016
  3252                                  
  3253                                  bss_start:
  3254                                  
  3255                                  ABSOLUTE bss_start
  3256                                  
  3257 00015B92 <res 00000006>          alignb 8 ; 25/12/2016
  3258                                  
  3259                                  	; 15/04/2016
  3260                                  	; TRDOS 386 (TRDOS v2.0)
  3261                                  	; 	80 interrupts 	
  3262                                  	; 11/03/2015
  3263                                  	; Interrupt Descriptor Table (20/08/2014)
  3264                                  idt:
  3265                                  	;resb	64*8 ; INT 0 to INT 3Fh
  3266                                  	; 15/04/2016
  3267 00015B98 <res 00000280>          	resb	80*8 ; INT 0 to INT 4Fh
  3268                                  
  3269                                  idt_end:
  3270                                  
  3271                                  ;alignb 4
  3272                                  
  3273                                  task_state_segment:
  3274                                  	; 24/03/2015
  3275 00015E18 <res 00000002>          tss.link:   resw 1
  3276 00015E1A <res 00000002>          	    resw 1
  3277                                  ; tss offset 4	
  3278 00015E1C <res 00000004>          tss.esp0:   resd 1
  3279 00015E20 <res 00000002>          tss.ss0:    resw 1
  3280 00015E22 <res 00000002>          	    resw 1	
  3281 00015E24 <res 00000004>          tss.esp1:   resd 1
  3282 00015E28 <res 00000002>          tss.ss1:    resw 1
  3283 00015E2A <res 00000002>          	    resw 1 	
  3284 00015E2C <res 00000004>          tss.esp2:   resd 1
  3285 00015E30 <res 00000002>          tss.ss2:    resw 1
  3286 00015E32 <res 00000002>          	    resw 1
  3287                                  ; tss offset 28
  3288 00015E34 <res 00000004>          tss.CR3:    resd 1
  3289 00015E38 <res 00000004>          tss.eip:    resd 1
  3290 00015E3C <res 00000004>          tss.eflags: resd 1
  3291                                  ; tss offset 40
  3292 00015E40 <res 00000004>          tss.eax:    resd 1		 		
  3293 00015E44 <res 00000004>          tss.ecx:    resd 1
  3294 00015E48 <res 00000004>          tss.edx:    resd 1
  3295 00015E4C <res 00000004>          tss.ebx:    resd 1
  3296 00015E50 <res 00000004>          tss.esp:    resd 1
  3297 00015E54 <res 00000004>          tss.ebp:    resd 1
  3298 00015E58 <res 00000004>          tss.esi:    resd 1
  3299 00015E5C <res 00000004>          tss.edi:    resd 1
  3300                                  ; tss offset 72
  3301 00015E60 <res 00000002>          tss.ES:     resw 1
  3302 00015E62 <res 00000002>          	    resw 1	
  3303 00015E64 <res 00000002>          tss.CS:	    resw 1
  3304 00015E66 <res 00000002>          	    resw 1
  3305 00015E68 <res 00000002>          tss.SS:	    resw 1
  3306 00015E6A <res 00000002>          	    resw 1
  3307 00015E6C <res 00000002>          tss.DS:	    resw 1
  3308 00015E6E <res 00000002>          	    resw 1
  3309 00015E70 <res 00000002>          tss.FS:	    resw 1
  3310 00015E72 <res 00000002>          	    resw 1
  3311 00015E74 <res 00000002>          tss.GS:	    resw 1
  3312 00015E76 <res 00000002>          	    resw 1		
  3313 00015E78 <res 00000002>          tss.LDTR:   resw 1
  3314 00015E7A <res 00000002>          	    resw 1
  3315                                  ; tss offset 100		
  3316 00015E7C <res 00000002>          	    resw 1		
  3317 00015E7E <res 00000002>          tss.IOPB:   resw 1
  3318                                  ; tss offset 104 
  3319                                  tss_end:
  3320                                  
  3321 00015E80 <res 00000004>          k_page_dir:  resd 1 ; Kernel's (System) Page Directory address
  3322                                  		    ; (Physical address = Virtual address)	 	
  3323 00015E84 <res 00000004>          memory_size: resd 1 ; memory size in pages
  3324 00015E88 <res 00000004>          free_pages:  resd 1 ; number of free pages		
  3325 00015E8C <res 00000004>          next_page:   resd 1 ; offset value in M.A.T. for
  3326                                  		    ; first free page search
  3327 00015E90 <res 00000004>          last_page:   resd 1 ; offset value in M.A.T. which
  3328                                  		    ; next free page search will be
  3329                                  		    ; stopped after it. (end of M.A.T.)
  3330 00015E94 <res 00000004>          first_page:  resd 1 ; offset value in M.A.T. which
  3331                                  		    ; first free page search
  3332                                  		    ; will be started on it. (for user)
  3333 00015E98 <res 00000004>          mat_size:    resd 1 ; Memory Allocation Table size in pages
  3334                                  
  3335                                  ; 20/11/2020
  3336                                  ;vbe2bios:    resw 1 ; VBE2 video bios ID (bochs/qemu)
  3337                                  ;		    ; (0B0C4h or 0B0C5h for bochs/plex86 vgabios)				
  3338                                  
  3339                                  ; 02/09/2014 (Retro UNIX 386 v1)
  3340                                  ; 04/12/2013 (Retro UNIX 8086 v1)
  3341 00015E9C <res 00000002>          CRT_START:   resw 1 	  ; starting address in regen buffer
  3342                                  			  ; NOTE: active page only	
  3343 00015E9E <res 00000010>          CURSOR_POSN: resw 8 ; cursor positions for video pages
  3344                                  ACTIVE_PAGE: 
  3345 00015EAE <res 00000001>          ptty: 	     resb 1 ; current tty
  3346                                  ; 01/07/2015 - 29/01/2016
  3347 00015EAF <res 00000001>          ccolor:	     resb 1 ; current color attribute
  3348                                  ; 26/10/2015
  3349                                  ; 07/09/2014
  3350 00015EB0 <res 00000014>          ttychr:      resw ntty+2 ; Character buffer (multiscreen)
  3351                                  
  3352                                  ; 18/05/2015 (03/06/2013 - Retro UNIX 8086 v1 feature only!)
  3353 00015EC4 <res 00000004>          p_time:      resd 1     ; present time (for systime & sysmdate)
  3354                                  
  3355                                  ; 18/05/2015 (16/08/2013 - Retro UNIX 8086 v1 feature only !)
  3356                                  ; (open mode locks for pseudo TTYs)
  3357                                  ; [ major tty locks (return error in any conflicts) ]
  3358 00015EC8 <res 00000014>          ttyl:        resw ntty+2 ; opening locks for TTYs.
  3359                                  
  3360                                  ; 15/04/2015 (Retro UNIX 386 v1)
  3361                                  ; 22/09/2013 (Retro UNIX 8086 v1)
  3362 00015EDC <res 0000000A>          wlist:       resb ntty+2 ; wait channel list (0 to 9 for TTYs)
  3363                                  ; 15/04/2015 (Retro UNIX 386 v1)
  3364                                  ;; 12/07/2014 -> sp_init set comm. parameters as 0E3h
  3365                                  ;; 0 means serial port is not available 
  3366                                  ;;comprm: ; 25/06/2014
  3367 00015EE6 <res 00000001>          com1p:       resb 1  ;;0E3h
  3368 00015EE7 <res 00000001>          com2p:       resb 1  ;;0E3h
  3369                                  
  3370                                  ; 17/11/2015
  3371                                  ; request for response (from the terminal)	
  3372 00015EE8 <res 00000002>          req_resp:    resw 1 			
  3373                                  ; 07/11/2015
  3374 00015EEA <res 00000001>          ccomport:    resb 1 ; current COM (serial) port
  3375                                  		    ; (0= COM1, 1= COM2)
  3376                                  ; 09/11/2015
  3377 00015EEB <res 00000001>          comqr:	     resb 1 ; 'query or response' sign (u9.s, 'sndc')
  3378                                  ; 07/11/2015
  3379 00015EEC <res 00000002>          rchar:	     resw 1 ; last received char for COM 1 and COM 2		
  3380 00015EEE <res 00000002>          schar:	     resw 1 ; last sent char for COM 1 and COM 2
  3381                                  
  3382                                  ; 22/08/2014 (RTC)
  3383                                  ; (Packed BCD)
  3384 00015EF0 <res 00000001>          time_seconds: resb 1
  3385 00015EF1 <res 00000001>          time_minutes: resb 1
  3386 00015EF2 <res 00000001>          time_hours:   resb 1
  3387 00015EF3 <res 00000001>          date_wday:    resb 1
  3388 00015EF4 <res 00000001>          date_day:     resb 1
  3389 00015EF5 <res 00000001>          date_month:   resb 1			
  3390 00015EF6 <res 00000001>          date_year:    resb 1
  3391 00015EF7 <res 00000001>          date_century: resb 1
  3392                                  
  3393                                  ; 24/01/2016
  3394 00015EF8 <res 00000004>          RTC_LH:	       resd 1
  3395 00015EFC <res 00000001>          RTC_WAIT_FLAG: resb 1
  3396 00015EFD <res 00000001>          USER_FLAG:     resb 1
  3397                                  ; 19/05/2016
  3398                                  ;RTC_second:
  3399 00015EFE <res 00000001>          RTC_2Hz:       resb 1 ;  from 2Hz interrupt to 1Hz timer event function	
  3400                                  
  3401                                  %include 'diskbss.s'	; UNINITIALIZED DISK (BIOS) DATA
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel) - v2.0.0 - diskbss.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 24/01/2016
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Turkish Rational DOS
    11                              <1> ; Operating System Project v2.0 by ERDOGAN TAN (Beginning: 04/01/2016)
    12                              <1> ;
    13                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    14                              <1> ; diskbss.inc (10/07/2015)
    15                              <1> ;
    16                              <1> ; Derived from 'IBM PC-XT-286' BIOS source code (1986) 
    17                              <1> ; ****************************************************************************
    18                              <1> 
    19                              <1> ; Retro UNIX 386 v1 Kernel - DISKBSS.INC
    20                              <1> ; Last Modification: 10/07/2015
    21                              <1> ;	(Unnitialized Disk Parameters Data section for 'DISKIO.INC') 
    22                              <1> 
    23 00015EFF <res 00000001>      <1> alignb 2
    24                              <1> 
    25                              <1> ;----------------------------------------
    26                              <1> ;	TIMER DATA AREA 		:
    27                              <1> ;----------------------------------------
    28                              <1> 
    29                              <1> TIMER_LH:	; 16/02/205
    30 00015F00 <res 00000002>      <1> TIMER_LOW:      resw	1               ; LOW WORD OF TIMER COUNT
    31 00015F02 <res 00000002>      <1> TIMER_HIGH:     resw	1               ; HIGH WORD OF TIMER COUNT
    32 00015F04 <res 00000001>      <1> TIMER_OFL:      resb 	1               ; TIMER HAS ROLLED OVER SINCE LAST READ
    33                              <1> 
    34                              <1> ;----------------------------------------
    35                              <1> ;	DISKETTE DATA AREAS		:
    36                              <1> ;----------------------------------------
    37                              <1> 
    38 00015F05 <res 00000001>      <1> SEEK_STATUS:	resb	1
    39 00015F06 <res 00000001>      <1> MOTOR_STATUS:	resb	1
    40 00015F07 <res 00000001>      <1> MOTOR_COUNT:	resb	1
    41 00015F08 <res 00000001>      <1> DSKETTE_STATUS:	resb	1
    42 00015F09 <res 00000007>      <1> NEC_STATUS:	resb	7
    43                              <1> 
    44                              <1> ;----------------------------------------
    45                              <1> ;	ADDITIONAL MEDIA DATA		:
    46                              <1> ;----------------------------------------
    47                              <1> 
    48 00015F10 <res 00000001>      <1> LASTRATE:	resb 	1
    49 00015F11 <res 00000001>      <1> HF_STATUS:	resb 	1
    50 00015F12 <res 00000001>      <1> HF_ERROR:	resb 	1
    51 00015F13 <res 00000001>      <1> HF_INT_FLAG:	resb 	1
    52 00015F14 <res 00000001>      <1> HF_CNTRL:	resb 	1
    53 00015F15 <res 00000004>      <1> DSK_STATE:	resb 	4
    54 00015F19 <res 00000002>      <1> DSK_TRK:	resb 	2
    55                              <1> 
    56                              <1> ;----------------------------------------
    57                              <1> ;	FIXED DISK DATA AREAS		:
    58                              <1> ;----------------------------------------
    59                              <1> 
    60 00015F1B <res 00000001>      <1> DISK_STATUS1:	resb 	1		; FIXED DISK STATUS
    61 00015F1C <res 00000001>      <1> HF_NUM:		resb 	1		; COUNT OF FIXED DISK DRIVES
    62 00015F1D <res 00000001>      <1> CONTROL_BYTE:	resb 	1		; HEAD CONTROL BYTE
    63                              <1> ;@PORT_OFF	resb	1		; RESERVED (PORT OFFSET)
    64                              <1> ;port1_off	resb	1		; Hard disk controller 1 - port offset
    65                              <1> ;port2_off	resb	1		; Hard idsk controller 2 - port offset
    66                              <1> 
    67 00015F1E <res 00000002>      <1> alignb 4
    68                              <1> 
    69                              <1> ;HF_TBL_VEC:	resd	1 		; Primary master disk param. tbl. pointer
    70                              <1> ;HF1_TBL_VEC:	resd	1		; Primary slave disk param. tbl. pointer
    71                              <1> HF_TBL_VEC: ; 22/12/2014	
    72 00015F20 <res 00000004>      <1> HDPM_TBL_VEC:	resd	1 		; Primary master disk param. tbl. pointer
    73 00015F24 <res 00000004>      <1> HDPS_TBL_VEC:	resd	1		; Primary slave disk param. tbl. pointer
    74 00015F28 <res 00000004>      <1> HDSM_TBL_VEC:	resd	1 		; Secondary master disk param. tbl. pointer
    75 00015F2C <res 00000004>      <1> HDSS_TBL_VEC:	resd	1		; Secondary slave disk param. tbl. pointer
    76                              <1> 
    77                              <1> ; 03/01/2015
    78 00015F30 <res 00000001>      <1> LBAMode:     	resb	1
    79                              <1> 
    80                              <1> ; *****************************************************************************
  3402                                  
  3403                                  ;;; Real Mode Data (10/07/2015 - BSS)
  3404                                  
  3405                                  ;alignb 2
  3406                                  
  3407                                  ; 10/01/2016
  3408                                  %include 'trdoskx.s'	; UNINITIALIZED KERNEL (Logical Drive & FS) DATA
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.2) - UNINITIALIZED DATA : trdoskx.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 30/08/2020
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 04/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from TRDOS Operating System v1.0 (8086) source code by Erdogan Tan
    11                              <1> ; TRDOS2.ASM (09/11/2011)
    12                              <1> ; ****************************************************************************
    13                              <1> ; DRV_INIT.ASM [26/09/2009] Last Update: 07/08/2011
    14                              <1> ; MAINPROG.ASM [17/01/2004] Last Update: 09/11/2011
    15                              <1> ; DIR.ASM      [17/01/2004] Last Update: 09/10/2011
    16                              <1> ; CMD_INTR.ASM [29/01/2005] Last update: 09/11/2011
    17                              <1> ; DRV_FAT.ASM  [07/07/2009] Last update: 21/08/2011
    18                              <1> 
    19 00015F31 <res 00000003>      <1> alignb 4
    20                              <1> 
    21                              <1> ; MAINPROG.ASM
    22 00015F34 <res 00000004>      <1> MainProgCfg_FileSize:   resd 1 ; 14/04/2016
    23 00015F38 <res 00000004>      <1> MainProgCfg_LineOffset: resd 1 ; 14/04/2016
    24                              <1> 
    25 00015F3C <res 00000004>      <1> Current_VolSerial: resd 1
    26                              <1> 
    27 00015F40 <res 00000004>      <1> Current_Dir_FCluster: resd 1
    28                              <1> 
    29 00015F44 <res 00000001>      <1> Current_Dir_Level: resb 1
    30 00015F45 <res 00000001>      <1> Current_FATType: resb 1
    31 00015F46 <res 00000001>      <1> Current_Drv: resb 1
    32 00015F47 <res 00000001>      <1> Current_Dir_Drv:   resb 1 ; '?'
    33 00015F48 <res 00000001>      <1>                    resb 1 ; ':'
    34 00015F49 <res 00000001>      <1> Current_Dir_Root:  resb 1 ; '/' 
    35 00015F4A <res 0000005A>      <1> Current_Directory: resb 90
    36 00015FA4 <res 00000001>      <1> End_Of_Current_Dir_Str: resb 1
    37 00015FA5 <res 00000001>      <1> Current_Dir_StrLen: resb 1   
    38                              <1> 
    39 00015FA6 <res 00000001>      <1> CursorColumn: 	resb 1
    40 00015FA7 <res 00000001>      <1> CmdArgStart:    resb 1
    41                              <1> 
    42                              <1> ; 03/02/2016
    43 00015FA8 <res 0000004E>      <1> Remark:		resb 78
    44                              <1> 
    45 00015FF6 <res 00000050>      <1> CommandBuffer: 	resb 80
    46                              <1> 
    47 00016046 <res 00000100>      <1> TextBuffer:	resb 256
    48                              <1> 
    49                              <1> MasterBootBuff:
    50 00016146 <res 000001BE>      <1> MasterBootCode: resb 1BEh
    51 00016304 <res 00000040>      <1> PartitionTable: resb 64
    52 00016344 <res 00000002>      <1> MBIDCode: resw 1
    53                              <1> 
    54                              <1> PTable_Buffer:
    55 00016346 <res 00000040>      <1> PTable_hd0: resb 64
    56 00016386 <res 00000040>      <1> PTable_hd1: resb 64
    57 000163C6 <res 00000040>      <1> PTable_hd2: resb 64
    58 00016406 <res 00000040>      <1> PTable_hd3: resb 64
    59                              <1> ; 15/07/2020
    60                              <1> ;PTable_ep0: resb 64
    61                              <1> ;PTable_ep1: resb 64
    62                              <1> ;PTable_ep2: resb 64
    63                              <1> ;PTable_ep3: resb 64
    64                              <1> 
    65                              <1> ; 13/08/2020
    66 00016446 <res 00000001>      <1> scount: resb 1 ; 16/05/2016 (diskio.s, 'int33h:')
    67 00016447 <res 00000001>      <1> 	resb 1
    68 00016448 <res 00000001>      <1> 	resb 1
    69 00016449 <res 00000001>      <1> 	resb 1
    70                              <1> 	
    71 0001644A <res 00000001>      <1> HD_LBA_yes: resb 1
    72 0001644B <res 00000001>      <1> PP_Counter: resb 1
    73 0001644C <res 00000001>      <1> EP_Counter: resb 1
    74                              <1> ; 13/08/2020
    75 0001644D <res 00000001>      <1> LD_Counter: resb 1
    76                              <1> 
    77                              <1> ; 30/08/2020
    78 0001644E <res 00000004>      <1> MBR_EP_StartSector: resd 1 
    79                              <1> 		; Extd partition start sector as in MBR
    80 00016452 <res 00000004>      <1> EP_StartSector: resd 1 ; next extd partition start sector
    81                              <1> 	; 15/07/2020	
    82                              <1>                 ;resd 1
    83                              <1>                 ;resd 1
    84                              <1> 
    85                              <1> ; 20/07/2020
    86 00016456 <res 00000200>      <1> DOSBootSectorBuff: resb 512
    87                              <1> ; 15/07/2020
    88                              <1> ;DOSBootSectorBuff: resb 446 ; 1BEh
    89                              <1> ;MiniPartitionTable: resb 64 ;  40h
    90                              <1> ;MiniPartitionMagic: resw  1 ;  02h 		
    91                              <1> 
    92                              <1> FAT_BuffDescriptor:
    93 00016656 <res 00000004>      <1> FAT_CurrentCluster: resd 1
    94 0001665A <res 00000001>      <1> FAT_BuffValidData: resb 1
    95 0001665B <res 00000001>      <1> FAT_BuffDrvName: resb 1
    96 0001665C <res 00000002>      <1> FAT_BuffOffset: resw 1
    97 0001665E <res 00000004>      <1> FAT_BuffSector: resd 1
    98                              <1> 
    99 00016662 <res 00000004>      <1> FAT_ClusterCounter: resd 1
   100 00016666 <res 00000004>      <1> LastCluster: resd 1
   101                              <1> 
   102                              <1> ; 16/05/2016
   103                              <1> ;; 18/03/2016 (TRDOS v2.0)
   104                              <1> ;ClusterBuffer_Valid: resb 1
   105                              <1> 
   106                              <1> Dir_BuffDescriptor:
   107 0001666A <res 00000001>      <1> DirBuff_DRV: resb 1
   108 0001666B <res 00000001>      <1> DirBuff_FATType: resb 1
   109 0001666C <res 00000001>      <1> DirBuff_ValidData: resb 1
   110 0001666D <res 00000002>      <1> DirBuff_CurrentEntry: resw 1
   111 0001666F <res 00000002>      <1> DirBuff_LastEntry: resw 1
   112 00016671 <res 00000004>      <1> DirBuff_Cluster: resd 1 
   113 00016675 <res 00000002>      <1> DirBuffer_Size: resw 1
   114                              <1> ;DirBuff_EntryCounter: resw 1
   115                              <1> 
   116                              <1> ; 01/02/2016
   117                              <1> ; these are on (real mode) segment 8000h and later
   118                              <1> ; FAT_Buffer:	resb 1536 ; 3 sectors
   119                              <1> ; Dir_Buffer:	resb 512*32
   120                              <1> ; Logical_DOSDisks:  resb 6656 ; 26 * 256 bytes
   121                              <1> 
   122                              <1> ; 18/01/2016
   123                              <1> 
   124 00016677 <res 00000004>      <1> FreeClusterCount: resd 1
   125                              <1> 
   126 0001667B <res 00000004>      <1> VolSize_Unit1:   resd 1
   127 0001667F <res 00000004>      <1> VolSize_Unit2:   resd 1
   128                              <1> 
   129 00016683 <res 00000004>      <1> Vol_Tot_Sec_Str_Start:	    resd 1
   130 00016687 <res 0000000A>      <1> Vol_Tot_Sec_Str: 	    resb 10
   131 00016691 <res 00000001>      <1> Vol_Tot_Sec_Str_End:	    resb 1
   132 00016692 <res 00000001>      <1> resb 1
   133 00016693 <res 00000004>      <1> Vol_Free_Sectors_Str_Start: resd 1
   134 00016697 <res 0000000A>      <1> Vol_Free_Sectors_Str:	    resb 10				
   135 000166A1 <res 00000001>      <1> Vol_Free_Sectors_Str_End:   resb 1
   136                              <1> 
   137                              <1> ; 10/02/2016
   138 000166A2 <res 00000001>      <1> RUN_CDRV: resb 1 ; CMD_INTR.ASM  ; 09/11/2011
   139                              <1> 
   140                              <1> ; 24/01/2016
   141 000166A3 <res 00000080>      <1> PATH_Array:     resb 128 ; DIR.ASM ; 09/10/2011
   142                              <1> ; 06/02/2016
   143 00016723 <res 00000004>      <1> CCD_DriveDT:	resd 1 ; DIR.ASM ; (word)
   144 00016727 <res 00000001>      <1> CCD_Level:	resb 1 ; DIR.ASM
   145 00016728 <res 00000001>      <1> Last_Dir_Level:	resb 1 ; DIR.ASM
   146                              <1> ;
   147 00016729 <res 00000002>      <1> CDLF_AttributesMask: resw 1 ; DIR.ASM
   148 0001672B <res 00000004>      <1> CDLF_FNAddress:	resd 1 ; DIR.ASM (word)
   149 0001672F <res 00000002>      <1> CDLF_DEType:	resw 1 ; DIR.ASM
   150                              <1> ;
   151 00016731 <res 00000001>      <1> CD_COMMAND:	resb 1 ; DIR.ASM
   152                              <1> 
   153 00016732 <res 00000002>      <1> alignb 4
   154                              <1> 
   155                              <1> ; 29/01/2016
   156 00016734 <res 00000001>      <1> Program_Exit:	resb 1 ; CMD_INTR.ASM  ; 09/11/2011
   157                              <1> 
   158                              <1> ;alignb 4
   159                              <1> ; 23/02/2016
   160 00016735 <res 00000001>      <1> disk_rw_op:	resb 1 ;  0 = disk read, 1 = disk write
   161                              <1> ;disk_rw_spt:	resb 1 ; sectors per track (<= 63) /// (<256)
   162                              <1> ; 31/01/2016
   163 00016736 <res 00000001>      <1> retry_count: 	resb 1 ; DISK_IO.ASM ; 20/07/2011 (CHS_RetryCount)
   164 00016737 <res 00000001>      <1> disk_rw_err: 	resb 1 ; DISK_IO.ASM ; (Disk_IO_err_code)
   165 00016738 <res 00000004>      <1> sector_count:	resd 1 ; DISK_IO.ASM ; (Disk_RW_SectorCount)
   166                              <1> 
   167                              <1> ; 06/02/2016 (long name)
   168 0001673C <res 00000002>      <1> FDE_AttrMask:	   resw 1 ; DIR.ASM
   169 0001673E <res 00000002>      <1> AmbiguousFileName: resw 1 ; DIR.ASM
   170 00016740 <res 00000001>      <1> PreviousAttr:	   resb 1 ; DIR.ASM
   171                              <1> ;	
   172 00016741 <res 00000001>      <1> LongNameFound:   resb 1	  ; DIR.ASM
   173 00016742 <res 00000001>      <1> LFN_EntryLength: resb 1   ; DIR.ASM
   174 00016743 <res 00000001>      <1> LFN_CheckSum:    resb 1   ; DIR.ASM
   175 00016744 <res 00000084>      <1> LongFileName:    resb 132 ; DIR.ASM
   176                              <1> 
   177                              <1> ;PATH_Array_Ptr: resw 1 ; DIR.ASM
   178 000167C8 <res 00000001>      <1> PATH_CDLevel:	 resb 1 ; DIR.ASM
   179 000167C9 <res 00000001>      <1> PATH_Level:	 resb 1 ; DIR.ASM
   180                              <1> 
   181                              <1> ; 07/02/2016
   182 000167CA <res 0000000D>      <1> Dir_File_Name:	resb 13 ; DIR.ASM ; 09/10/2011
   183                              <1> 
   184                              <1> ; 10/02/2016
   185 000167D7 <res 0000000D>      <1> Dir_Entry_Name:	resb 13 ; DIR.ASM
   186                              <1> 
   187                              <1> alignb 2
   188                              <1> 
   189 000167E4 <res 00000002>      <1> AttributesMask: resw 1 ; CMD_INTR.ASM ; 09/11/2011
   190                              <1> 
   191                              <1> ; 10/02/2016 (128 bytes -> 126 bytes)
   192                              <1> ; 08/02/2016
   193                              <1> ;FFF Structure (128 bytes) ; DIR.ASM ; 09/10/2011
   194 000167E6 <res 00000001>      <1> FindFile_Drv:		  resb 1
   195 000167E7 <res 00000041>      <1> FindFile_Directory:	  resb 65
   196 00016828 <res 0000000D>      <1> FindFile_Name:		  resb 13
   197                              <1> FindFile_LongNameEntryLength:
   198 00016835 <res 00000001>      <1> FindFile_LongNameYes: 	  resb 1 ; Sign for longname procedures
   199                              <1> ;Above 80 bytes form
   200                              <1> ;TR-DOS Source/Destination File FullName Format/Structure
   201 00016836 <res 00000002>      <1> FindFile_AttributesMask:  resw 1
   202 00016838 <res 00000020>      <1> FindFile_DirEntry:	  resb 32
   203 00016858 <res 00000004>      <1> FindFile_DirFirstCluster: resd 1
   204 0001685C <res 00000004>      <1> FindFile_DirCluster:	  resd 1
   205 00016860 <res 00000002>      <1> FindFile_DirEntryNumber:  resw 1
   206 00016862 <res 00000002>      <1> FindFile_MatchCounter:	  resw 1
   207 00016864 <res 00000002>      <1> FindFile_Reserved:	  resw 1 ; 06/03/2016
   208                              <1> 
   209 00016866 <res 00000004>      <1> First_Path_Pos: resd 1	; DIR.ASM ; 09/10/2011
   210 0001686A <res 00000004>      <1> Last_Slash_Pos: resd 1	; DIR.ASM 
   211                              <1> 
   212                              <1> ; 10/02/2016
   213 0001686E <res 00000002>      <1> File_Count:     resw 1 	; DIR.ASM ; 09/10/2011
   214 00016870 <res 00000002>      <1> Dir_Count:      resw 1
   215 00016872 <res 00000004>      <1> Total_FSize:    resd 1
   216 00016876 <res 00000004>      <1> TFS_Dec_Begin:  resd 1
   217 0001687A <res 0000000A>      <1>                 resb 10
   218 00016884 <res 00000001>      <1> TFS_Dec_End:    resb 1
   219                              <1> 
   220 00016885 <res 00000001>      <1> PrintDir_RowCounter: resb 1
   221                              <1> 
   222 00016886 <res 00000002>      <1> alignb 4
   223                              <1> ; 15/02/2015 ('show' command variables)
   224 00016888 <res 00000004>      <1> Show_FDT:	resd 1
   225 0001688C <res 00000004>      <1> Show_LDDDT:	resd 1
   226 00016890 <res 00000004>      <1> Show_Cluster:	resd 1
   227 00016894 <res 00000004>      <1> Show_FileSize:	resd 1
   228 00016898 <res 00000004>      <1> Show_FilePointer: resd 1
   229 0001689C <res 00000002>      <1> Show_ClusterPointer: resw 1
   230 0001689E <res 00000002>      <1> Show_ClusterSize: resw 1
   231 000168A0 <res 00000001>      <1> Show_RowCount:	resb 1
   232                              <1> 
   233 000168A1 <res 00000003>      <1> alignb 4
   234                              <1> ; 21/02/2016
   235 000168A4 <res 00000004>      <1> DelFile_FNPointer:	resd 1 ; ; CMD_INTR.ASM (word) ; 09/11/2011
   236                              <1> ; 27/02/2016
   237                              <1> ; DIR.ASM (09/10/2011)
   238 000168A8 <res 00000004>      <1> DelFile_FCluster:	resd 1
   239 000168AC <res 00000002>      <1> DelFile_EntryCounter:	resw 1
   240 000168AE <res 00000001>      <1> DelFile_LNEL:		resb 1
   241 000168AF <res 00000001>      <1> resb 1
   242                              <1> 
   243                              <1> ; DIR.ASM
   244 000168B0 <res 00000004>      <1> mkdir_DirName_Offset: 	resd 1
   245 000168B4 <res 00000004>      <1> mkdir_FFCluster:	resd 1
   246 000168B8 <res 00000004>      <1> mkdir_LastDirCluster:	resd 1
   247 000168BC <res 00000004>      <1> mkdir_FreeSectors:	resd 1
   248 000168C0 <res 00000002>      <1> mkdir_attrib:		resw 1 
   249 000168C2 <res 00000001>      <1> mkdir_SecPerClust:	resb 1
   250 000168C3 <res 00000001>      <1> mkdir_add_new_cluster:	resb 1
   251 000168C4 <res 0000000D>      <1> mkdir_Name:		resb 13
   252 000168D1 <res 00000002>      <1> resw 1 ; 01/03/2016
   253                              <1> ; 27/02/2016
   254 000168D3 <res 00000001>      <1> RmDir_MultiClusters:	resb 1  
   255 000168D4 <res 00000004>      <1> RmDir_DirEntryOffset:	resd 1 ; 01/03/2016 (word -> dword)
   256 000168D8 <res 00000004>      <1> RmDir_ParentDirCluster: resd 1
   257 000168DC <res 00000004>      <1> RmDir_DirLastCluster:   resd 1
   258 000168E0 <res 00000004>      <1> RmDir_PreviousCluster:  resd 1
   259                              <1> ; 22/02/2016
   260 000168E4 <res 00000001>      <1> UPDLMDT_CDirLevel:	resb 1
   261 000168E5 <res 00000004>      <1> UPDLMDT_CDirFCluster:	resd 1
   262                              <1> 	
   263 000168E9 <res 00000003>      <1> alignb 4
   264                              <1> ; DRV_FAT.ASM ; 21/08/2011
   265 000168EC <res 00000004>      <1> gffc_next_free_cluster:  resd 1
   266 000168F0 <res 00000004>      <1> gffc_first_free_cluster: resd 1
   267 000168F4 <res 00000004>      <1> gffc_last_free_cluster:  resd 1
   268                              <1> 
   269                              <1> ;29/04/2016
   270                              <1> Cluster_Index: ; resd 1
   271                              <1> ; 22/02/2016
   272 000168F8 <res 00000004>      <1> ClusterValue:	resd 1
   273                              <1> ; 04/03/2016
   274 000168FC <res 00000001>      <1> Attributes:	resb 1 
   275                              <1> ;;CFS_error:  resb 1 ;; 01/03/2016
   276 000168FD <res 00000001>      <1> resb 1
   277 000168FE <res 00000001>      <1> CFS_OPType: resb 1
   278 000168FF <res 00000001>      <1> CFS_Drv:    resb 1
   279 00016900 <res 00000004>      <1> CFS_CC:	    resd 1
   280 00016904 <res 00000004>      <1> CFS_FAT32FSINFOSEC: resd 1
   281 00016908 <res 00000004>      <1> CFS_FAT32FC: resd 1
   282                              <1> 
   283                              <1> ; 27/02/2016
   284                              <1> ;alignb 4
   285 0001690C <res 00000004>      <1> glc_prevcluster: resd 1 ; DRV_FAT.ASM (21/08/2011)
   286                              <1> ; 22/10/2016
   287 00016910 <res 00000004>      <1> glc_index:	 resd 1 ;  Last Cluster Index (22/10/2016)	
   288                              <1> 
   289                              <1> ; DIR.ASM
   290 00016914 <res 00000002>      <1> DLN_EntryNumber: resw 1
   291 00016916 <res 00000001>      <1> DLN_40h:	 resb 1
   292                              <1> ; 28/02/2016
   293 00016917 <res 00000001>      <1> TCC_FATErr:	 resb 1 ; DRV_FAT.ASM
   294                              <1> 
   295                              <1> alignb 4
   296                              <1> ; DIR.ASM (09/10/2011)
   297 00016918 <res 00000002>      <1> LCDE_EntryIndex: resw 1 ; LCDE_EntryOffset
   298 0001691A <res 00000002>      <1> LCDE_ClusterSN:  resw 1
   299 0001691C <res 00000004>      <1> LCDE_Cluster: 	 resd 1
   300 00016920 <res 00000004>      <1> LCDE_ByteOffset: resd 1
   301                              <1> 
   302                              <1> ;alignb4
   303                              <1> ; 06/03/2016 (word -> dword)
   304                              <1> ; CMD_INTR.ASM (01/08/2010)
   305 00016924 <res 00000004>      <1> SourceFilePath:	     resd 1
   306 00016928 <res 00000004>      <1> DestinationFilePath: resd 1
   307                              <1> 
   308                              <1> ;alignb 4
   309                              <1> ; 06/03/2016
   310                              <1> ; FILE.ASM (09/10/2011)
   311                              <1> ;Source File Structure (same with 'Find File' Structure)
   312 0001692C <res 00000001>      <1> SourceFile_Drv:			resb 1
   313 0001692D <res 00000041>      <1> SourceFile_Directory:		resb 65
   314 0001696E <res 0000000D>      <1> SourceFile_Name:		resb 13
   315                              <1> SourceFile_LongNameEntryLength: 
   316 0001697B <res 00000001>      <1> SourceFile_LongNameYes:		resb 1 ; Sign for longname procedures
   317                              <1> ;Above 80 bytes
   318                              <1> ;is TR-DOS Source File FullName Format/Structure
   319 0001697C <res 00000002>      <1> SourceFile_AttributesMask:	resw 1
   320 0001697E <res 00000020>      <1> SourceFile_DirEntry:		resb 32
   321 0001699E <res 00000004>      <1> SourceFile_DirFirstCluster:	resd 1
   322 000169A2 <res 00000004>      <1> SourceFile_DirCluster:		resd 1
   323 000169A6 <res 00000002>      <1> SourceFile_DirEntryNumber:	resw 1
   324 000169A8 <res 00000002>      <1> SourceFile_MatchCounter:	resw 1
   325                              <1> ; 16/03/2016
   326 000169AA <res 00000001>      <1> SourceFile_SecPerClust:		resb 1
   327 000169AB <res 00000001>      <1> SourceFile_Reserved:		resb 1
   328                              <1> ; Above is 128 bytes
   329                              <1> 
   330                              <1> ;Destination File Structure (same with 'Find File' Structure)
   331 000169AC <res 00000001>      <1> DestinationFile_Drv:		resb 1
   332 000169AD <res 00000041>      <1> DestinationFile_Directory: 	resb 65
   333 000169EE <res 0000000D>      <1> DestinationFile_Name:		resb 13
   334                              <1> DestinationFile_LongNameEntryLength:
   335 000169FB <res 00000001>      <1> DestinationFile_LongNameYes:	resb 1 ; Sign for longname procedures
   336                              <1> ;Above 80 bytes
   337                              <1> ;is TR-DOS Destination File FullName Format/Structure
   338 000169FC <res 00000002>      <1> DestinationFile_AttributesMask: resw 1
   339 000169FE <res 00000020>      <1> DestinationFile_DirEntry:	resb 32
   340 00016A1E <res 00000004>      <1> DestinationFile_DirFirstCluster: resd 1
   341 00016A22 <res 00000004>      <1> DestinationFile_DirCluster:	resd 1
   342 00016A26 <res 00000002>      <1> DestinationFile_DirEntryNumber: resw 1
   343 00016A28 <res 00000002>      <1> DestinationFile_MatchCounter:	resw 1
   344                              <1> ; 16/03/2016
   345 00016A2A <res 00000001>      <1> DestinationFile_SecPerClust:	resb 1
   346 00016A2B <res 00000001>      <1> DestinationFile_Reserved:	resb 1
   347                              <1> ; Above is 128 bytes
   348                              <1> 
   349                              <1> ; 24/04/2016
   350 00016A2C <res 00000002>      <1> resw 1
   351                              <1> 
   352                              <1> ; 10/03/2016
   353                              <1> ; FILE.ASM
   354 00016A2E <res 00000001>      <1> move_cmd_phase:	   resb 1
   355 00016A2F <res 00000001>      <1> msftdf_sf_df_drv:  resb 1
   356 00016A30 <res 00000004>      <1> msftdf_drv_offset: resd 1
   357                              <1> 
   358                              <1> ; 11/03/2016
   359                              <1> ; DRV_FAT.ASM (21/08/2011)
   360 00016A34 <res 00000004>      <1> FAT_anc_LCluster:  resd 1
   361 00016A38 <res 00000004>      <1> FAT_anc_FFCluster: resd 1
   362                              <1> 
   363                              <1> ;alignb 4
   364                              <1> 
   365                              <1> ; 14/03/2016
   366                              <1> ; TRDOS 386 = TRDOS v2.0 feature only !
   367                              <1> ; 'allocate_memory_block' in 'memory.s'
   368 00016A3C <res 00000004>      <1> mem_ipg_count:	resd 1 ; page count (for contiguous allocation)
   369 00016A40 <res 00000004>      <1> mem_pg_count:	resd 1 ; page count (for count down)
   370 00016A44 <res 00000004>      <1> mem_aperture:	resd 1 ; contiguous free pages (current)
   371 00016A48 <res 00000004>      <1> mem_max_aperture: resd 1 ; maximum value of contiguous free pages
   372 00016A4C <res 00000004>      <1> mem_pg_pos:	resd 1 ; mem. position (page #) of current aperture
   373 00016A50 <res 00000004>      <1> mem_max_pg_pos: resd 1 ; mem. position (page #) of max. aperture
   374                              <1> 
   375                              <1> ; 15/03/2016
   376                              <1> ; FILE.ASM ('copy_source_file_to_destination_file')
   377 00016A54 <res 00000001>      <1> copy_cmd_phase:       resb 1
   378 00016A55 <res 00000001>      <1> csftdf_rw_err:	      resb 1
   379 00016A56 <res 00000001>      <1> DestinationFileFound: resb 1
   380 00016A57 <res 00000001>      <1> csftdf_cdrv: 	      resb 1
   381 00016A58 <res 00000004>      <1> csftdf_filesize:      resd 1
   382                              <1> ; TRDOS386 (TRDOS v2.0)
   383 00016A5C <res 00000004>      <1> csftdf_sf_mem_addr:   resd 1
   384 00016A60 <res 00000004>      <1> csftdf_sf_mem_bsize:  resd 1
   385                              <1> ;
   386                              <1> 
   387 00016A64 <res 00000004>      <1> csftdf_sf_cluster:    resd 1 ; 16/03/2016
   388 00016A68 <res 00000004>      <1> csftdf_df_cluster:    resd 1
   389                              <1> ; 16/03/2016
   390 00016A6C <res 00000004>      <1> csftdf_r_size:        resd 1
   391 00016A70 <res 00000004>      <1> csftdf_w_size:        resd 1
   392 00016A74 <res 00000004>      <1> csftdf_sf_rbytes:     resd 1
   393 00016A78 <res 00000004>      <1> csftdf_df_wbytes:     resd 1
   394 00016A7C <res 00000001>      <1> csftdf_percentage:    resb 1
   395                              <1> ; 17/03/2016
   396 00016A7D <res 00000001>      <1> csftdf_videopage:     resb 1
   397 00016A7E <res 00000002>      <1> csftdf_cursorpos:     resw 1
   398 00016A80 <res 00000004>      <1> csftdf_sf_drv_dt:     resd 1
   399 00016A84 <res 00000004>      <1> csftdf_df_drv_dt:     resd 1
   400                              <1> 
   401                              <1> ; 21/03/2016
   402                              <1> ; 20/03/2016
   403                              <1> ; FILE.ASM
   404 00016A88 <res 00000004>      <1> createfile_Name_Offset:  resd 1
   405 00016A8C <res 00000004>      <1> createfile_FreeSectors:  resd 1 
   406 00016A90 <res 00000004>      <1> createfile_size:         resd 1
   407 00016A94 <res 00000004>      <1> createfile_FFCluster:    resd 1 ; 11/03/2016
   408 00016A98 <res 00000004>      <1> createfile_LastDirCluster: resd 1
   409 00016A9C <res 00000004>      <1> createfile_Cluster:      resd 1
   410 00016AA0 <res 00000004>      <1> createfile_PCluster:     resd 1
   411 00016AA4 <res 00000001>      <1> createfile_attrib:	 resb 1
   412 00016AA5 <res 00000001>      <1> createfile_SecPerClust:  resb 1
   413 00016AA6 <res 00000002>      <1> createfile_DirIndex:     resw 1
   414 00016AA8 <res 00000004>      <1> createfile_CCount:	 resd 1
   415 00016AAC <res 00000002>      <1> createfile_BytesPerSec:	 resw 1 ; 23/03/2016
   416 00016AAE <res 00000001>      <1> createfile_wfc:	         resb 1
   417 00016AAF <res 00000001>      <1> createfile_UpdatePDir:	 resb 1 ; 31/03/2016
   418                              <1> 
   419                              <1> ;alignb 4
   420                              <1> 
   421                              <1> ; 11/04/2016
   422 00016AB0 <res 00000002>      <1> env_var_length:	   resw 1
   423                              <1> 
   424 00016AB2 <res 00000002>      <1> alignb 4
   425                              <1> 
   426                              <1> ; 25/04/2016
   427 00016AB4 <res 00000001>      <1> readi.valid:	resb 1 ; valid data (>0 = valid for readi)
   428 00016AB5 <res 00000001>      <1> readi.drv:	resb 1 ; drive number (0, 1,2,3,4..)
   429 00016AB6 <res 00000001>      <1> readi.spc:	resb 1 ; sectors per cluster for 'readi' drive
   430 00016AB7 <res 00000001>      <1> readi.s_index:  resb 1 ; sector index in current cluster (buffer)
   431 00016AB8 <res 00000004>      <1> readi.sector:	resd 1 ; current disk sector
   432 00016ABC <res 00000002>      <1> readi.bpc:	resw 1 ; bytes per cluster - 1
   433 00016ABE <res 00000002>      <1> readi.offset:	resw 1 ; byte offset in cluster buffer
   434 00016AC0 <res 00000004>      <1> readi.cluster:  resd 1 ; current cluster number
   435 00016AC4 <res 00000004>      <1> readi.c_index:	resd 1 ; cluster index of the current cluster (0,1,2,3..)
   436 00016AC8 <res 00000004>      <1> readi.fclust:	resd 1 ; first cluster of the current cluster
   437 00016ACC <res 00000004>      <1> readi.fs_index: resd 1 ; sector index in disk/file section (for Singlix FS)
   438                              <1> ;readi.buffer:	resd 1 ; readi sector buffer address
   439                              <1> 
   440                              <1> ;alignb 4
   441                              <1> 
   442 00016AD0 <res 00000001>      <1> writei.valid:	resb 1 ; valid data (>0 = valid for writei)
   443 00016AD1 <res 00000001>      <1> writei.drv:	resb 1 ; drive number (0, 1,2,3,4..)
   444 00016AD2 <res 00000001>      <1> writei.spc:	resb 1 ; sectors per cluster for 'writei' drive
   445 00016AD3 <res 00000001>      <1> writei.s_index: resb 1 ; sector index in current cluster (buffer)
   446 00016AD4 <res 00000004>      <1> writei.sector:	resd 1 ; current disk sector
   447 00016AD8 <res 00000002>      <1> writei.bpc:	resw 1 ; bytes per cluster - 1
   448 00016ADA <res 00000002>      <1> writei.offset:	resw 1 ; byte offset in cluster buffer
   449 00016ADC <res 00000004>      <1> writei.cluster: resd 1 ; current cluster number
   450 00016AE0 <res 00000004>      <1> writei.c_index:	resd 1 ; cluster index of the current cluster (0,1,2,3..)
   451 00016AE4 <res 00000004>      <1> writei.fclust:  resd 1 ; first cluster of the current cluster
   452 00016AE8 <res 00000004>      <1> writei.fs_index: resd 1 ; sector index in disk/file section (for Singlix FS)
   453                              <1> ;writei.buffer:	resd 1 ; writei sector buffer address
   454 00016AEC <res 00000004>      <1> writei.lclust:	resd 1 ; writei last cluster (mget_w) ; 23/10/2016
   455 00016AF0 <res 00000004>      <1> writei.l_index:	resd 1 ; writei last cluster index (mget_w) ; 23/10/2016
   456 00016AF4 <res 00000001>      <1> writei.ofn:	resb 1 ; open file number (to be written) ; 23/10/2016
   457                              <1> 
   458 00016AF5 <res 00000003>      <1> alignb 4
   459                              <1> 
   460                              <1> ; 29/04/2016
   461 00016AF8 <res 00000004>      <1> Run_CDirFC:	resd 1
   462 00016AFC <res 00000001>      <1> Run_Auto_Path:	resb 1
   463 00016AFD <res 00000001>      <1> Run_Manual_Path: resb 1 ; 0 -> auto path sequence needed
   464 00016AFE <res 00000001>      <1> EXE_ID:		resb 1	
   465 00016AFF <res 00000001>      <1> EXE_dot:	resb 1
   466                              <1> 
   467                              <1> ; 06/05/2016
   468 00016B00 <res 00000004>      <1> mainprog_return_addr: resd 1
   469 00016B04 <res 00000004>      <1> last_error:	resd 1  ; this will be used to return error code to MainProg
   470                              <1> 			; 'lasterror' keyword will be used later to get the
   471                              <1> 			; last error code/number/status.
   472                              <1> ; 12/05/2016
   473 00016B08 <res 00000004>      <1> video_eax:	resd 1  ; eax return value of video function
   474                              <1> 
   475                              <1> ; 01/06/2016
   476 00016B0C <res 00000004>      <1> user_buffer:	resd 1  ; 'diskio.s' (INT 33h, Function 08h, floppy disk type)
   477                              <1> 
   478                              <1> ; 21/05/2016 - TRDOS 386 ('swap/switch', 'rswap', [u.pri])
   479 00016B10 <res 00000001>      <1> priority:	resb 1  ; running priority level of process (0,1,2)
   480                              <1> 			; (run queue which is process comes from)
   481                              <1> ; 22/05/2016 - TRDOS 386 ('set_run_sequence', 'rtc_int', 'u_timer')
   482 00016B11 <res 00000001>      <1> p_change:	resb 1  ; process change status (for timer events)
   483                              <1> ; 23/05/2016 - TRDOS 386 ('clock')
   484 00016B12 <res 00000001>      <1> multi_tasking:	resb 1   ; Multi Tasking status (0 = disabled, >0 = enabled)
   485                              <1> 			; (EBX will return with user buffer addr or disk type)
   486                              <1> ; 07/06/2016
   487 00016B13 <res 00000001>      <1> timer_events:	resb 1  ; number of (active) timer events, <= 16		
   488                              <1> 
   489                              <1> ; 24/06/2016
   490 00016B14 <res 00000001>      <1> w_str_cmd:	resb 1	; WRITE_STRING command (0,1,2,3) ; video.s
   491 00016B15 <res 00000001>      <1> p_crt_mode:	resb 1  ; previous video mode (=3 or 0), backup mark/sign
   492                              <1> ; 26/06/2016
   493 00016B16 <res 00000001>      <1> p_crt_page:	resb 1  ; previous active page (for 'set_mode')
   494                              <1> ; 04/07/2016
   495 00016B17 <res 00000001>      <1> noclearmem:	resb 1  ; if set, 'SET MODE' (INT 31h) function (AH = 4)
   496                              <1> 			; will not clear the video memory
   497                              <1> 			; (usable for graphics modes only)
   498                              <1> alignb 2
   499 00016B18 <res 00000002>      <1> CRT_LEN:	resw 1  ; length of regen buffer in bytes
   500 00016B1A <res 00000010>      <1> cursor_pposn:	resw 8  ; cursor positions backup
   501                              <1> 
   502                              <1> ; 10/07/2016 ('VGA_FONT_SETUP', INT 43H address for x86 real mode bios)
   503 00016B2A <res 00000004>      <1> VGA_INT43H:	resd 1	; 0 = default (not configured by user)
   504                              <1> 			; 0FFFFFFFFh = user defined fonts
   505                              <1> 			; address:
   506                              <1> 			; 	vgafont8
   507                              <1> 			; 	vgafont16
   508                              <1> 			; 	vgafont14
   509                              <1> 
   510                              <1> ; 25/07/2016
   511 00016B2E <res 00000001>      <1> VGA_MTYPE:	resb 1  ; 0=CTEXT,1=MTEXT,2=CGA,3=PLANAR1,4=PLANAR4,5=LINEAR 
   512                              <1> 
   513                              <1> ; 23/10/2016
   514 00016B2F <res 00000001>      <1> setfmod		resb 1	; update last modification date&time sign (if >0)
   515                              <1> 			; (it is Open File Number + 1, if > 0)
   516                              <1> alignb 4
   517                              <1> 
   518                              <1> ; 16/10/2016
   519 00016B30 <res 00000004>      <1> FFF_UBuffer:	resd 1  ; User's buffer address for FFF & FNF system calls 
   520                              <1> ; 15/10/2016
   521 00016B34 <res 00000001>      <1> FFF_Valid:	resb 1  ; Find First File Structure validation byte
   522                              <1> 			; 0  = invalid (Find Next File can't use FFF struct)
   523                              <1> 			; >0 = valid, return type for FFF and Find Next File
   524                              <1> 			; 24 = basic parameters, 24 bytes
   525                              <1> 			; 128 = entire FFF structure/table, 128 bytes
   526                              <1> ; 16/10/2016 (FFF_Attrib: resw 1)
   527 00016B35 <res 00000001>      <1> FFF_Attrib:	resb 1	; Find First File attributes for Find Next File (LB)
   528 00016B36 <res 00000001>      <1> FFF_RType:	resb 1  ; FFF return type (0 = Basic, >0 = complete) (HB)
   529                              <1> ; 16/10/2016 - 05/10/2016 (Set Working Path)
   530 00016B37 <res 00000001>      <1> SWP_inv_fname:	resb 1	; Set Working Path - Invalid File Name
   531 00016B38 <res 00000002>      <1> SWP_Mode:	resw 1	; Set Working Path - Mode
   532 00016B3A <res 00000001>      <1> SWP_DRV:	resb 1	; Set Working Path - Drive	
   533 00016B3B <res 00000001>      <1> SWP_DRV_chg:	resb 1	; Set Working Path - Drive Change
   534                              <1> 
   535                              <1> ; 27/02/2017
   536 00016B3C <res 00000001>      <1> fpready:	resb 1	; '80387 fpu is ready' flag	
   537                              <1> 
   538                              <1> ; 08/10/2016
   539 00016B3D <res 00000009>      <1> device_name:    resb 9  ; capitalized (and zero padded) device canem 
   540                              <1> 			; (example: "TTY0",0,0,0,0,0")
   541                              <1> 
   542 00016B46 <res 00000002>      <1> alignb 4
   543                              <1> 
   544                              <1> ; 08/10/2016
   545                              <1> ; 07/10/2016
   546                              <1> ; Table of kernel devices (which do not use installable device drivers)
   547                              <1> ; has been coded into KERNEL (trdosk9.s) 
   548                              <1> ; 07/10/2016
   549                              <1> ; 8 installable device drivers available to install (NUMIDEV)
   550 00016B48 <res 00000020>      <1> IDEV_PGDIR: resd NUMIDEV
   551                              <1> 			; Page directories of installable device drivers
   552                              <1> 			;
   553                              <1> 			; Note: Virtual start address is always 400000h
   554                              <1> 			; (end of the 1st 4MB). [org 400000h]
   555                              <1> 			; Segments: KCODE, KDATA
   556                              <1> 			; Method: call 400000h (after changing page dir) 	
   557                              <1> 			; Query code located at the start (400000h).
   558                              <1> 			; Query code returns with
   559                              <1> 			;   eax = device type and driver version
   560                              <1> 			;         AL = Device Type minor
   561                              <1> 			;         AH = Device Type major
   562                              <1> 			;         Byte 16-23 : Version minor
   563                              <1> 			;	  Byte 24-31 : Version major - 1
   564                              <1> 			;		       (0:0 -> 1.0)
   565                              <1> 			;   ebx = initialization code address
   566                              <1> 			;   ecx = configuration table address
   567                              <1> 			;   edx = description table address
   568                              <1> 			;   esi = device (default) name address (ASCIIZ)
   569                              <1> 			;	 (name has "/DEV/" prefix)		
   570                              <1> 			;   edi = dispatch table address
   571                              <1> 			;        (for calling kernel-device functions)
   572                              <1> 			;   ebp = address table address
   573                              <1> 			; Initialization code returns with
   574                              <1> 			;   eax = open code address
   575                              <1> 			;   ecx = close code address 
   576                              <1> 			;   ebx = read code address
   577                              <1> 			;   edx = write code address 	
   578                              <1> 			;   esi = IOCTL code address
   579                              <1> 			;   edi = dispatch table address
   580                              <1> 			;   ebp = address table address
   581                              <1> 			; Address Table:
   582                              <1> 			;    Offset 0  : open code address
   583                              <1> 			;    Offset 4  : read code address
   584                              <1> 			;    Offset 8  : write code address
   585                              <1> 			;    Offset 12 : close code address
   586                              <1> 			;    Offset 16 : IOCTL code address
   587                              <1> 			;    Offset 20 : initialization code address
   588                              <1> 			;    Offset 24 : description table address
   589                              <1> 			;    Offset 28 : configuration table address
   590                              <1> 			;    Offset 32 : device name address
   591                              <1> 			;    Offset 36 : dispatch table address
   592                              <1> 			;          (for calling kernel-device functions)
   593                              <1> 
   594 00016B68 <res 00000040>      <1> IDEV_NAME:  resb 8*NUMIDEV 
   595                              <1> 			; 8 byte names of installable device drivers
   596                              <1> 
   597 00016BA8 <res 00000008>      <1> IDEV_TYPE:  resb NUMIDEV ; Driver type of installable device drivers
   598 00016BB0 <res 00000008>      <1> IDEV_FLAGS: resb NUMIDEV ; Device access parameters for installable
   599                              <1>                          ; device drivers (These values are set while
   600                              <1> 			 ; the device driver is being loaded.)
   601 00016BB8 <res 00000020>      <1> IDEV_OADDR: resd NUMIDEV ; open function addr for installable dev driver
   602 00016BD8 <res 00000020>      <1> IDEV_CADDR: resd NUMIDEV ; close function addr for installable dev driver
   603 00016BF8 <res 00000020>      <1> IDEV_RADDR: resd NUMIDEV ; read function addr for installable dev driver
   604 00016C18 <res 00000020>      <1> IDEV_WADDR: resd NUMIDEV ; write function addr for installable dev driver
   605                              <1> 	
   606                              <1> ; 08/10/2016	
   607                              <1> ; 07/10/2016
   608                              <1> ; Device Open and Access parameters
   609 00016C38 <res 0000001E>      <1> DEV_ACCESS:	 resb NUMOFDEVICES   ; bit 0 = accessable by normal users
   610                              <1> 				     ; bit 1 = read access permission
   611                              <1> 				     ; bit 2 = write access permission
   612                              <1> 				     ; bit 3 = IOCTL permission to users
   613                              <1> 				     ; bit 4 = block device if it is set	
   614                              <1> 				     ; bit 5 = 16 bit or 1024 byte data
   615                              <1> 				     ; bit 6 = 32 bit or 2048 byte data
   616                              <1> 				     ; bit 7 = installable device driver
   617 00016C56 <res 0000001E>      <1> DEV_R_OWNER:	 resb NUMOFDEVICES   ; Reading owner no (u.uid) of devices		
   618 00016C74 <res 0000001E>      <1> DEV_R_OPENCOUNT: resb NUMOFDEVICES   ; Reading open count 
   619 00016C92 <res 0000001E>      <1> DEV_W_OWNER:	 resb NUMOFDEVICES   ; Writing owner no (u.uid) of devices		
   620 00016CB0 <res 0000001E>      <1> DEV_W_OPENCOUNT: resb NUMOFDEVICES   ; Writing open count
   621 00016CCE <res 0000001E>      <1> DEV_DRIVER:	 resb NUMOFDEVICES   ; device driver number (1 to 7Fh)
   622                              <1> 				     ; *if bit 7 is set (80 to FFh)
   623                              <1> 				     ; *if it is installable device driver
   624                              <1> 				     ; *index (0 to 7Fh)
   625                              <1> 				     ; otherwise it is kernel device index
   626 00016CEC <res 0000001E>      <1> DEV_OPENMODE:	 resb NUMOFDEVICES   ; 1 = read mode
   627                              <1> 				     ; 2 = write mode
   628                              <1> 				     ; 3 = read & write 	  
   629                              <1> 				     ; 0 = not open (free)		
   630 00016D0A <res 00000078>      <1> DEV_NAME_PTR:    resd NUMOFDEVICES   ; pointers to name addresses of drivers
   631                              <1> 				     ; Address base: KDEV_NAME+		
   632                              <1> 				     ; or IDEV_NAME+
   633 00016D82 <res 00000078>      <1> DEV_R_POINTER:	 resd NUMOFDEVICES   ; reading pointer, writing pointer	
   634 00016DFA <res 00000078>      <1> DEV_W_POINTER:	 resd NUMOFDEVICES   ; sector number if block device
   635                              <1> 				     ; character offset if char device
   636 00016E72 <res 00000002>      <1> alignb 4
   637                              <1> 
   638                              <1> ; 06/10/2016
   639                              <1> ; Open File Parameters
   640 00016E74 <res 00000028>      <1> OF_FCLUSTER:	resd OPENFILES  ; First clusters of open files
   641 00016E9C <res 0000000A>      <1> OF_DRIVE:	resb OPENFILES  ; Logical DOS drive numbers of open files 
   642 00016EA6 <res 0000000A>      <1> OF_MODE:	resb OPENFILES  ; Open mode (1 = read, 2 = write, 3 = r&w) 
   643 00016EB0 <res 0000000A>      <1> OF_STATUS:	resb OPENFILES  ; (bit 0 = read, bit 1 = write)
   644 00016EBA <res 0000000A>      <1> OF_OPENCOUNT:	resb OPENFILES  ; Open counts of open files
   645 00016EC4 <res 00000028>      <1> OF_POINTER:	resd OPENFILES	; File seek/read/write pointer
   646 00016EEC <res 00000028>      <1> OF_SIZE:	resd OPENFILES	; File sizes of open files (in bytes)
   647 00016F14 <res 00000028>      <1> OF_DIRFCLUSTER:	resd OPENFILES  ; Directory First Clusters of open files
   648 00016F3C <res 00000028>      <1> OF_DIRCLUSTER:	resd OPENFILES  ; Directory (Entry) Clusters of open files
   649 00016F64 <res 00000028>      <1> OF_VOLUMEID:	resd OPENFILES  ; Vol ID for removable drives of open files
   650 00016F8C <res 00000028>      <1> OF_CCLUSTER:	resd OPENFILES  ; Current clusters of open files
   651 00016FB4 <res 00000028>      <1> OF_CCINDEX:	resd OPENFILES  ; Cluster index numbers of current clusters
   652                              <1> ; 24/10/2016
   653 00016FDC <res 00000014>      <1> OF_DIRENTRY:	resw OPENFILES  ; Directory entry index no. in dir cluster 
   654                              <1> 				; Sector index = entry index / 16
   655                              <1> ;alignb 2
   656                              <1> 
   657 00016FF0 <res 00000060>      <1> DTA:		resd 24		; Find First File data transfer area
   658                              <1> 
   659                              <1> ; 19/12/2016
   660 00017050 <res 00000001>      <1> tcallback:	resb 1		; Timer callback method flag for 'systimer'
   661 00017051 <res 00000001>      <1> trtc:		resb 1		; Timer interrupt type flag for 'systimer'
   662                              <1> ; 20/02/2017
   663 00017052 <res 00000001>      <1> no_page_swap:	resb 1		; Swap lock for Signal Response Byte pages 
   664                              <1> ;;15/01/2017
   665                              <1> ; 02/01/2017
   666                              <1> ;;intflg:	resb 1		; software interrupt in progress signal
   667                              <1> 				; (for timer interrupt)
   668                              <1> 
   669 00017053 <res 00000001>      <1> alignb 4
   670                              <1> ; 13/04/2017
   671 00017054 <res 0000001E>      <1> DEV_INTR:	resb NUMOFDEVICES ; Device Interrupt (IRQ) number + 1	
   672                              <1> 				; (0= not available, 1= IRQ 0, 16= IRQ 15)
   673 00017072 <res 00000040>      <1> DEV_INT_HNDLR:	resd 16		; Device Interrupt Handler addr, if > 0 	
   674                              <1> 
   675                              <1> 
   676                              <1> ;alignb 4
   677                              <1> 
   678                              <1> ; 26/02/2017 ; IRQ Callback parameters ('syscalbac')
   679                              <1> ;Index: ; 0 to 8
   680                              <1> ;	0 = IRQ3, 1 = IRQ4, 2 = IRQ5, 3 = IRQ7
   681                              <1> ;	4 = IRQ9, 5 = IRQ10, 6 = IRQ11, 7 = IRQ12, 8 = IRQ13  
   682 000170B2 <res 00000009>      <1> IRQ.owner:	resb 9		; owner, 0 = free, >0 = [u.uno]
   683 000170BB <res 00000009>      <1> IRQ.dev:	resb 9		; 0 = default/kernel, >0 = device number
   684 000170C4 <res 00000009>      <1> IRQ.method:	resb 9 		; 0 = Signal Response Byte, 1 = Callback
   685 000170CD <res 00000009>      <1> IRQ.srb:	resb 9 		; Signal Response/Return Byte value
   686 000170D6 <res 00000024>      <1> IRQ.addr:	resd 9		; Rignal Response Byte address (physical)
   687                              <1> 				; or Callback service address (virtual)
   688                              <1> ; 28/02/2017
   689 000170FA <res 00000004>      <1> IRQ_cr3:	resd 1		; for saving cr3 register in IRQ handler
   690 000170FE <res 00000001>      <1> IRQnum:		resb 1		; IRQ number for IRQ handler (trdosk8.s)
   691                              <1> 
   692                              <1> ; 10/04/2017
   693                              <1> ; 03/04/2017
   694                              <1> ; UNINITIALIZED AUDIO DATA
   695 000170FF <res 00000001>      <1> alignb 4
   696 00017100 <res 00000001>      <1> audio_pci:	resb 1
   697 00017101 <res 00000001>      <1> audio_device:	resb 1
   698 00017102 <res 00000001>      <1> audio_mode:	resb 1
   699 00017103 <res 00000001>      <1> audio_intr:	resb 1
   700 00017104 <res 00000001>      <1> audio_busy:	resb 1  ; Busy flag for audio irq ; 21/04/2017
   701 00017105 <res 00000001>      <1> audio_reserved: resb 1
   702 00017106 <res 00000002>      <1> audio_io_base:	resw 1 	; Base I/O address of audio device
   703 00017108 <res 00000004>      <1> audio_dev_id:	resd 1	; BUS/DEV/FN ; 00000000BBBBBBBBDDDDDFFF00000000
   704 0001710C <res 00000004>      <1> audio_vendor:	resd 1
   705 00017110 <res 00000004>      <1> audio_stats_cmd: resd 1
   706                              <1> ;
   707 00017114 <res 00000004>      <1> audio_buffer:	resd 1	; virtual address of user's audio buffer
   708 00017118 <res 00000004>      <1> audio_p_buffer:	resd 1	; Physical address of user's audio buffer
   709 0001711C <res 00000004>      <1> audio_buff_size: resd 1 ; user's audio buffer size (half buffer size) 
   710 00017120 <res 00000004>      <1> audio_dma_buff: resd 1  ; dma buffer address
   711 00017124 <res 00000004>      <1> audio_dmabuff_size: resd 1 ; dma buffer size (2 * half buffer size)
   712 00017128 <res 00000001>      <1> audio_flag:	resb 1  ; dma buffer flag (1st half = 0, 2nd half = 1)
   713 00017129 <res 00000001>      <1> audio_user:	resb 1	; user number of the owner
   714 0001712A <res 00000001>      <1> audio_cb_mode:	resb 1	; 0 = signal response byte method
   715                              <1> 			; 1 = callback method
   716                              <1> 			; 2 = s.r.b. method with auto increment
   717 0001712B <res 00000001>      <1> audio_srb:	resb 1	; signal response byte value
   718 0001712C <res 00000004>      <1> audio_cb_addr:	resd 1  ; callback service address or s.r.b. address
   719                              <1> 			; (s.r.b. addr is physical, cbs addr is virtual)
   720                              <1> 
   721 00017130 <res 00000001>      <1> audio_bps:	resb 1  ; selected mode: 8 bit, 16 bit
   722 00017131 <res 00000001>      <1> audio_stmo:	resb 1	; selected mode: mono /stereo
   723 00017132 <res 00000002>      <1> audio_freq: 	resw 1	; sampling rate
   724                              <1> 
   725                              <1> ; 21/04/2017
   726 00017134 <res 00000001>      <1> audio_play_cmd: resb 1  ; Play/Stop command (1 = play, 0 = stop)
   727                              <1> audio_civ: ; 28/05/2017 ; Current Buffer Index (AC'97)
   728 00017135 <res 00000001>      <1> audio_flag_eol:	resb 1  ; End of Link status (vt8233, EOL/FLAG)
   729                              <1> 
   730                              <1> audio_master_volume:
   731 00017136 <res 00000001>      <1> audio_master_volume_l: resb 1 ; sound volume (lineout) left channel
   732 00017137 <res 00000001>      <1> audio_master_volume_r: resb 1 ; sound volume (lineout) right channel
   733                              <1> 
   734                              <1> alignb 4
   735                              <1> ; 28/05/2017
   736                              <1> ; AC'97 Audio Controller Base Adress Registers
   737 00017138 <res 00000002>      <1> NAMBAR:		resw 1	; Native Audio Mixer Base Address
   738 0001713A <res 00000002>      <1> NABMBAR:	resw 1	; Native Audio Bus Mastering Base Address
   739                              <1> 	
   740                              <1> ;alignb 4
   741                              <1> ; 21/04/2017
   742 0001713C <res 00000400>      <1> audio_bdl_buff:	resd 32*8  ; VT8233 (AC97) BDL Buffer Size
   743                              <1> ; 12/05/2017
   744 0001753C <res 00000004>      <1> base_addr:	resd 1	; 'direct_memory_access' (memory.s)
   745                              <1> 
   746                              <1> ; 28/08/2017
   747                              <1> ; 20/08/2017
   748 00017540 <res 00000001>      <1> 		resb 1  ;
   749 00017541 <res 00000001>      <1> dma_user:	resb 1	; user number for sysdma
   750 00017542 <res 00000001>      <1> dma_channel:	resb 1	; dma channel for sysdma
   751 00017543 <res 00000001>      <1> dma_mode:	resb 1  ; dma mode for sysdma	
   752 00017544 <res 00000004>      <1> dma_addr:	resd 1	; dma buffer physical addr for sysdma
   753 00017548 <res 00000004>      <1> dma_size:	resd 1  ; dma buffer size (in bytes) for sysdma
   754 0001754C <res 00000004>      <1> dma_start:	resd 1  ; dma start address for sysdma
   755 00017550 <res 00000004>      <1> dma_count:	resd 1  ; dma count (in bytes) for sysdma 
   756                              <1> 
   757 00017554 <res 00008AAC>      <1> alignb 65536
   758                              <1> ; 09/08/2017
   759                              <1> ; 12/05/2017
   760 00020000 <res 00010000>      <1> sb16_dma_buffer: resb 65536 ; DMA buffer for sb16 audio playing.
  3409                                  ; 24/01/2016
  3410                                  %include 'ubss.s'	; UNINITIALIZED KERNEL (USER) DATA
     1                              <1> ; ****************************************************************************
     2                              <1> ; TRDOS386.ASM (TRDOS 386 Kernel - v2.0.0) - UNINITIALIZED USER DATA : ubss.s
     3                              <1> ; ----------------------------------------------------------------------------
     4                              <1> ; Last Update: 28/02/2017
     5                              <1> ; ----------------------------------------------------------------------------
     6                              <1> ; Beginning: 24/01/2016
     7                              <1> ; ----------------------------------------------------------------------------
     8                              <1> ; Assembler: NASM version 2.11 (trdos386.s)
     9                              <1> ; ----------------------------------------------------------------------------
    10                              <1> ; Derived from 'Retro UNIX 386 Kernel - v0.2.1.0' source code by Erdogan Tan
    11                              <1> ; ux.s (04/12/2015)
    12                              <1> ; ****************************************************************************
    13                              <1> 
    14                              <1> ; Retro UNIX 386 v1 Kernel - ux.s
    15                              <1> ; Last Modification: 04/12/2015
    16                              <1> ;
    17                              <1> ; ///////// RETRO UNIX 386 V1 SYSTEM DEFINITIONS ///////////////
    18                              <1> ; (Modified from 
    19                              <1> ;	Retro UNIX 8086 v1 system definitions in 'UNIX.ASM', 01/09/2014)
    20                              <1> ; ((UNIX.ASM (RETRO UNIX 8086 V1 Kernel), 11/03/2013 - 01/09/2014))
    21                              <1> ; ----------------------------------------------------------------------------
    22                              <1> ; Derived from UNIX Operating System (v1.0 for PDP-11) 
    23                              <1> ; (Original) Source Code by Ken Thompson (1971-1972)
    24                              <1> ; <Bell Laboratories (17/3/1972)>
    25                              <1> ; <Preliminary Release of UNIX Implementation Document>
    26                              <1> ; (Section E10 (17/3/1972) - ux.s)
    27                              <1> ; ****************************************************************************
    28                              <1> 
    29                              <1> alignb 2
    30                              <1> 
    31                              <1> inode:
    32                              <1> 	; 11/03/2013. 
    33                              <1> 	;Derived from UNIX v1 source code 'inode' structure (ux).
    34                              <1> 	;i.
    35                              <1> 
    36 00030000 <res 00000002>      <1> 	i.flgs:	 resw 1
    37 00030002 <res 00000001>      <1> 	i.nlks:	 resb 1
    38 00030003 <res 00000001>      <1> 	i.uid:	 resb 1
    39                              <1>         ;i.size:  resw 1 ; size
    40 00030004 <res 00000002>      <1> 	resw 1 ; 29/04/2016
    41 00030006 <res 00000010>      <1> 	i.dskp:	 resw 8 ; 16 bytes
    42 00030016 <res 00000004>      <1> 	i.ctim:	 resd 1
    43 0003001A <res 00000004>      <1> 	i.mtim:	 resd 1
    44 0003001E <res 00000002>      <1> 	i.rsvd:  resw 1 ; Reserved (ZERO/Undefined word for UNIX v1.)
    45                              <1> 
    46                              <1> I_SIZE	equ $ - inode 
    47                              <1> 
    48                              <1> process:
    49                              <1> 	; 19/12/2016
    50                              <1> 	; 21/05/2016
    51                              <1> 	; 19/05/2016 - TRDOS 386 (TRDOS v2.0)
    52                              <1> 	; 06/05/2015 - Retro UNIX 386 v1
    53                              <1> 	; 11/03/2013 - 05/02/2014 (Retro UNIX 8086 v1)
    54                              <1> 	;Derived from UNIX v1 source code 'proc' structure (ux).
    55                              <1> 	;p.
    56                              <1> 	
    57 00030020 <res 00000020>      <1>         p.pid:   resw nproc
    58 00030040 <res 00000020>      <1>         p.ppid:  resw nproc
    59 00030060 <res 00000020>      <1>         p.break: resw nproc
    60 00030080 <res 00000010>      <1>         p.ttyc:  resb nproc ; console tty in Retro UNIX 8086 v1.
    61 00030090 <res 00000010>      <1> 	p.waitc: resb nproc ; waiting channel in Retro UNIX 8086 v1.
    62 000300A0 <res 00000010>      <1> 	p.link:	 resb nproc
    63 000300B0 <res 00000010>      <1> 	p.stat:	 resb nproc
    64                              <1> 
    65                              <1> 	; 06/05/2015 (Retro UNIX 386 v1 feature only !) 
    66 000300C0 <res 00000040>      <1> 	p.upage: resd nproc ; Physical address of the process's
    67                              <1> 			    ; 'user' structure
    68                              <1> 	; 21/05/2016	
    69                              <1> 	; 19/05/2016 (TRDOS 386 feature only!)
    70 00030100 <res 00000010>      <1> 	p.timer: resb nproc ; number of timer events of the processs
    71                              <1> 
    72                              <1> 	; 19/12/2016
    73 00030110 <res 00000040>      <1> 	p.tcb:	resd nproc ; timer callback service address (if > 0)
    74                              <1> 			  		 			 	  
    75                              <1> P_SIZE	equ $ - process
    76                              <1> 
    77                              <1> ; fsp table (original UNIX v1)
    78                              <1> ;
    79                              <1> ;Entry
    80                              <1> ;          15                                      0
    81                              <1> ;  1     |---|---------------------------------------|
    82                              <1> ;        |r/w|       i-number of open file           |
    83                              <1> ;        |---|---------------------------------------| 
    84                              <1> ;        |               device number               |
    85                              <1> ;        |-------------------------------------------|
    86                              <1> ;    (*) | offset pointer, i.e., r/w pointer to file |
    87                              <1> ;        |-------------------------------------------| 
    88                              <1> ;        |  flag that says    | number of processes  |
    89                              <1> ;        |   file deleted     | that have file open  |
    90                              <1> ;        |-------------------------------------------| 
    91                              <1> ;  2     |                                           |
    92                              <1> ;        |-------------------------------------------| 
    93                              <1> ;        |                                           |
    94                              <1> ;        |-------------------------------------------|
    95                              <1> ;        |                                           |
    96                              <1> ;        |-------------------------------------------|
    97                              <1> ;        |                                           |
    98                              <1> ;        |-------------------------------------------| 
    99                              <1> ;  3     |                                           | 
   100                              <1> ;        |                                           |  
   101                              <1> ;
   102                              <1> ; (*) Retro UNIX 386 v1 modification: 32 bit offset pointer 
   103                              <1> 
   104                              <1> 
   105                              <1> ; 15/04/2015
   106 00030150 <res 000001F4>      <1> fsp:	 resb nfiles * 10 ; 11/05/2015 (8 -> 10)
   107 00030344 <res 00000002>      <1> idev:	 resw 1 ; device number is 1 byte in Retro UNIX 8086 v1 !
   108 00030346 <res 00000002>      <1> cdev:    resw 1 ; device number is 1 byte in Retro UNIX 8086 v1 !
   109                              <1> ; 18/05/2015
   110                              <1> ; 26/04/2013 device/drive parameters (Retro UNIX 8086 v1 feature only!)
   111                              <1> ; 'UNIX' device numbers (as in 'cdev' and 'u.cdrv')
   112                              <1> ;	0 -> root device (which has Retro UNIX 8086 v1 file system)
   113                              <1> ; 	1 -> mounted device (which has Retro UNIX 8086 v1 file system)
   114                              <1> ; 'Retro UNIX 8086 v1' device numbers: (for disk I/O procedures)
   115                              <1> ;	0 -> fd0 (physical drive, floppy disk 1), physical drive number = 0
   116                              <1> ;	1 -> fd1 (physical drive, floppy disk 2), physical drive number = 1
   117                              <1> ;	2 -> hd0 (physical drive, hard disk 1), physical drive number = 80h
   118                              <1> ;	3 -> hd1 (physical drive, hard disk 2), physical drive number = 81h
   119                              <1> ;	4 -> hd2 (physical drive, hard disk 3), physical drive number = 82h
   120                              <1> ;	5 -> hd3 (physical drive, hard disk 4), physical drive number = 83h
   121 00030348 <res 00000001>      <1> rdev:	 resb 1 ; root device number ; Retro UNIX 8086 v1 feature only!
   122                              <1> 	        ; as above, for physical drives numbers in following table
   123 00030349 <res 00000001>      <1> mdev:	 resb 1 ; mounted device number ; Retro UNIX 8086 v1 feature only!
   124                              <1> ; 15/04/2015
   125 0003034A <res 00000001>      <1> active:	 resb 1 
   126 0003034B <res 00000001>      <1> 	 resb 1 ; 09/06/2015
   127 0003034C <res 00000002>      <1> mnti:	 resw 1
   128 0003034E <res 00000002>      <1> mpid:	 resw 1
   129 00030350 <res 00000002>      <1> rootdir: resw 1
   130                              <1> 
   131                              <1> ; 21/05/2016 - TRDOS 386 (TRDOS v2.0) - priority levels, 3 run queues 
   132                              <1> runq:
   133 00030352 <res 00000002>      <1> runq_event:	 resw 1 ; high priority, 'run for event'            ; 2
   134 00030354 <res 00000002>      <1> runq_normal:	 resw 1 ; normal/regular priority, 'run as reqular' ; 1
   135 00030356 <res 00000002>      <1> runq_background: resw 1 ; low priority, 'run on background'         ; 0
   136                              <1> ;
   137 00030358 <res 00000001>      <1> imod:	 resb 1
   138 00030359 <res 00000001>      <1> smod:	 resb 1
   139 0003035A <res 00000001>      <1> mmod:	 resb 1
   140 0003035B <res 00000001>      <1> sysflg:	 resb 1
   141                              <1> 
   142                              <1> alignb 4
   143                              <1> 
   144                              <1> user:
   145                              <1> 	; 13/01/2017
   146                              <1> 	; 19/12/2016
   147                              <1> 	; 21/05/2016 - TRDOS 386 (TRDOS v2.0) 
   148                              <1> 	; 	       [u.pri] usage method modification
   149                              <1> 	; 04/12/2015 
   150                              <1> 	; 18/10/2015
   151                              <1> 	; 12/10/2015
   152                              <1> 	; 21/09/2015
   153                              <1> 	; 24/07/2015
   154                              <1> 	; 16/06/2015
   155                              <1> 	; 09/06/2015
   156                              <1> 	; 11/05/2015
   157                              <1> 	; 16/04/2015 (Retro UNIX 386 v1 - 32 bit modifications)
   158                              <1> 	; 10/10/2013
   159                              <1> 	; 11/03/2013. 
   160                              <1> 	;Derived from UNIX v1 source code 'user' structure (ux).
   161                              <1> 	;u.
   162                              <1> 
   163 0003035C <res 00000004>      <1> 	u.sp:	  resd 1 ; esp (kernel stack at the beginning of 'sysent')
   164 00030360 <res 00000004>      <1> 	u.usp:	  resd 1 ; esp (kernel stack points to user's registers)
   165 00030364 <res 00000004>      <1> 	u.r0:	  resd 1 ; eax
   166 00030368 <res 00000002>      <1> 	u.cdir:	  resw 1
   167 0003036A <res 0000000A>      <1> 	u.fp:	  resb 10
   168 00030374 <res 00000004>      <1> 	u.fofp:	  resd 1
   169 00030378 <res 00000004>      <1> 	u.dirp:	  resd 1
   170 0003037C <res 00000004>      <1> 	u.namep:  resd 1
   171 00030380 <res 00000004>      <1> 	u.off:	  resd 1
   172 00030384 <res 00000004>      <1> 	u.base:	  resd 1
   173 00030388 <res 00000004>      <1> 	u.count:  resd 1
   174 0003038C <res 00000004>      <1> 	u.nread:  resd 1
   175 00030390 <res 00000004>      <1> 	u.break:  resd 1 ; break
   176 00030394 <res 00000002>      <1> 	u.ttyp:	  resw 1 
   177                              <1> 	; 10/01/2017 (TRDOS 386, relocation and dword alignment)
   178                              <1> 	; tty number (rtty, rcvt, wtty)
   179 00030396 <res 00000001>      <1> 	u.ttyn:	  resb 1 ; 28/07/2013 - Retro Unix 8086 v1 feature only !
   180 00030397 <res 00000001>      <1> 	u.resb:   resb 1 ; 10/01/2017 (TRDOS 386, temporary)
   181 00030398 <res 00000010>      <1> 	u.dirbuf: resb 16 ; 04/12/2015 (10 -> 16) 
   182                              <1> 	;u.pri:	  resw 1 ; 14/02/2014
   183 000303A8 <res 00000001>      <1> 	u.quant:  resb 1 ; Retro UNIX 8086 v1 Feature only ! (uquant)
   184 000303A9 <res 00000001>      <1> 	u.pri:	  resb 1 ; Modification: 21/05/2016 (priority levels: 0, 1, 2)
   185 000303AA <res 00000002>      <1> 	u.intr:	  resw 1
   186 000303AC <res 00000002>      <1> 	u.quit:	  resw 1
   187                              <1> 	;u.emt:	  resw 1 ; 10/10/2013
   188                              <1> 	;u.ilgins: resw 1 ; 10/01/2017
   189 000303AE <res 00000002>      <1> 	u.cdrv:	  resw 1 ; cdev
   190 000303B0 <res 00000001>      <1> 	u.uid:	  resb 1 ; uid
   191 000303B1 <res 00000001>      <1> 	u.ruid:	  resb 1
   192 000303B2 <res 00000001>      <1> 	u.bsys:	  resb 1
   193 000303B3 <res 00000001>      <1> 	u.uno:	  resb 1
   194 000303B4 <res 00000004>      <1>         u.upage:  resd 1 ; 16/04/2015 - Retro Unix 386 v1 feature only !
   195 000303B8 <res 00000004>      <1> 	u.pgdir:  resd 1 ; 09/03/2015 (page dir addr of process)
   196 000303BC <res 00000004>      <1> 	u.ppgdir: resd 1 ; 06/05/2015 (page dir addr of the parent process)
   197 000303C0 <res 00000004>      <1> 	u.pbase:  resd 1 ; 20/05/2015 (physical base/transfer address)
   198 000303C4 <res 00000002>      <1> 	u.pcount: resw 1 ; 20/05/2015 (byte -transfer- count for page)
   199                              <1> 	;u.pncount: resw 1 
   200                              <1> 		; 16/06/2015 (byte -transfer- count for page, 'namei', 'mkdir')
   201                              <1> 	;u.pnbase:  resd 1 
   202                              <1> 		; 16/06/2015 (physical base/transfer address, 'namei', 'mkdir')
   203                              <1> 			 ; 09/06/2015
   204 000303C6 <res 00000001>      <1> 	u.kcall:  resb 1 ; The caller is 'namei' (dskr) or 'mkdir' (dskw) sign		
   205 000303C7 <res 00000001>      <1> 	u.brwdev: resb 1 ; Block device number for direct I/O (bread & bwrite)
   206                              <1> 			 ; 24/07/2015 - 24/06/2015
   207                              <1> 	;u.args:  resd 1 ; arguments list (line) offset from start of [u.upage]
   208                              <1> 			 ; (arg list/line is from offset [u.args] to 4096 in [u.upage])
   209                              <1> 			 ; ([u.args] points to argument count -argc- address offset)
   210                              <1>  			 ; 24/06/2015	  	
   211                              <1> 	;u.core:  resd 1 ; physical start address of user's memory space (for sys exec)
   212                              <1> 	;u.ecore: resd 1 ; physical end address of user's memory space (for sys exec)
   213                              <1> 	; last error number
   214 000303C8 <res 00000004>      <1> 	u.error:  resd 1 ; 28/07/2013 - 09/03/2015 
   215                              <1> 		        ; Retro UNIX 8086/386 v1 feature only!
   216                              <1> 			; 21/09/2015 (debugging - page fault analyze)
   217 000303CC <res 00000004>      <1> 	u.pfcount: resd 1 ; page fault count for (this) process (for sys geterr)
   218                              <1> 		; 19/12/2016 (TRDOS 386)	
   219 000303D0 <res 00000004>      <1> 	u.tcb:	  resd 1 ; Timer callback address/flag which will be used by timer int
   220                              <1> 		; 13/01/2017 (TRDOS 386)
   221 000303D4 <res 00000001>      <1> 	u.t_lock: resb 1 ; Timer interrupt (callback) lock (unlocked by 'sysrele')
   222 000303D5 <res 00000001>      <1> 	u.t_mode: resb 1 ; running mode during timer interrupt (0= system, 0FFh= user)
   223                              <1> 		; 26/02/2017 (TRDOS 386)
   224 000303D6 <res 00000001>      <1> 	u.irqc:	  resb 1  ; Count of IRQ callback services (IRQs in use)
   225                              <1> 		; 28/02/2017 (TRDOS 386) 
   226 000303D7 <res 00000001>      <1> 	u.irqwait: resb 1 ; IRQ waiting for callback service flag (IRQ number, If > 0)
   227 000303D8 <res 00000001>      <1> 	u.r_lock:  resb 1 ; 'IRQ callback service is in progress' flag (IRQ lock)
   228 000303D9 <res 00000001>      <1> 	u.r_mode:  resb 1 ; running mode during hadware interrupt	
   229                              <1> 		; 27/02/2017 (TRDOS 386) 
   230 000303DA <res 00000001>      <1> 	u.fpsave: resb 1  ; TRDOS 386, 'save/restore FPU registers' flag
   231 000303DB <res 00000001>      <1> alignb 4
   232 000303DC <res 0000005E>      <1> 	u.fpregs: resb 94 ; 94 byte area for saving and restoring FPU registers	
   233                              <1> 
   234 0003043A <res 00000002>      <1> alignb 4
   235                              <1> 
   236                              <1> U_SIZE	equ $ - user
   237                              <1> 
   238                              <1> ; 18/10/2015 - Retro UNIX 386 v1 (local variables for 'namei' and 'sysexec')
   239 0003043C <res 00000004>      <1> pcore:  resd 1  ; physical start address of user's memory space (for sys exec)
   240 00030440 <res 00000004>      <1> ecore:  resd 1  ; physical address of user's stack/last page (for sys exec)
   241 00030444 <res 00000004>      <1> nbase:	resd 1	; physical base address for 'namei' & 'sysexec'
   242 00030448 <res 00000002>      <1> ncount: resw 1	; remain byte count in page for 'namei' & 'sysexec'
   243 0003044A <res 00000002>      <1> argc:	resw 1	; argument count for 'sysexec'
   244 0003044C <res 00000004>      <1> argv:	resd 1	; argument list (recent) address for 'sysexec'
   245                              <1> 
   246                              <1> ; 03/06/2015 - Retro UNIX 386 v1 Beginning
   247                              <1> ; 07/04/2013 - 31/07/2013 - Retro UNIX 8086 v1
   248 00030450 <res 00000001>      <1> rw: 	 resb 1 ;; Read/Write sign (iget)
   249                              <1> 
   250                              <1> ;alignb 4
   251                              <1> 
   252                              <1> ; 24/04/2016
   253 00030451 <res 00000004>      <1> ii:		resd 1 ; first cluster of the program file
   254 00030455 <res 00000004>      <1> i.size:		resd 1 ; size of the program file
  3411                                  
  3412 00030459 <res 00000003>          alignb 4
  3413                                  
  3414                                  ; 23/05/2016 (TRDOS 386)
  3415                                  ; 14/10/2015 (Retro UNIX 386 v1, 'unix386.s')
  3416 0003045C <res 00000004>          cr3reg:	 resd 1  ; cr3 register content at the beginning of the timer
  3417                                  		 ; (or RTC) interrupt handler.
  3418                                  
  3419                                  ; 10/12/2016 (callback)
  3420                                  ; 10/06/2016
  3421                                  ; 19/05/2016
  3422                                  ; 18/05/2016 - TRDOS 386 feature only !
  3423 00030460 <res 00000100>          timer_set: resd 16*4   ; 256 bytes memory space for 16 timer events
  3424                                  	; Timer Event Structure: (max. 16 timer events, 16*16 bytes)
  3425                                  	;       Owner:	        resb 1 ; 0 = free
  3426                                  	;		  	       ;>0 = process number (u.uno)
  3427                                  	;	Callback:	resb 1 ; 0 = response byte address (phy)
  3428                                  	;				 1 = callback address (virtual)				
  3429                                  	;	Interrupt:      resb 1 ; 0 = Timer interrupt (or none)
  3430                                  	;		   	       ; 1 = Real Time Clock interrupt 
  3431                                  	;	Response:       resb 1 ; 0 to 255, signal return value
  3432                                  	;	Count Limit:	resd 1 ; count of ticks (total/set)
  3433                                  	;	Current Count: 	resd 1 ; count of ticks (current)
  3434                                  	;	Response Addr:  resd 1 ; response byte (pointer) address
  3435                                  	;			       ; (or callback -user service- address)	
  3436                                  
  3437                                  ;; Memory (swap) Data (11/03/2015)
  3438                                  ; 09/03/2015
  3439 00030560 <res 00000002>          swpq_count: resw 1 ; count of pages on the swap queue
  3440 00030562 <res 00000004>          swp_drv:    resd 1 ; logical drive description table address of the swap drive/disk
  3441 00030566 <res 00000004>          swpd_size:  resd 1 ; size of swap drive/disk (volume) in sectors (512 bytes). 		  				
  3442 0003056A <res 00000004>          swpd_free:  resd 1 ; free page blocks (4096 bytes) on swap disk/drive (logical)
  3443 0003056E <res 00000004>          swpd_next:  resd 1 ; next free page block
  3444 00030572 <res 00000004>          swpd_last:  resd 1 ; last swap page block	
  3445                                  
  3446 00030576 <res 00000002>          alignb 4
  3447                                  
  3448                                  ; 10/07/2015
  3449                                  ; 28/08/2014
  3450 00030578 <res 00000004>          error_code:	resd 1
  3451                                  ; 29/08/2014
  3452 0003057C <res 00000004>          FaultOffset: 	resd 1
  3453                                  ; 21/09/2015
  3454 00030580 <res 00000004>          PF_Count:	resd 1	; total page fault count
  3455                                  		       	; (for debugging - page fault analyze)
  3456                                  		 	; 'page_fault_handler' (memory.inc)
  3457                                  			; 'sysgeterr' (u9.s)
  3458                                  
  3459                                  ; 29/04/2016 (TRDOS 386 = TRDOS v2.0)
  3460                                  ; 22/08/2015 (Retro UNIX 386 v1)
  3461                                  buffer: 
  3462 00030584 <res 00000008>          	resb	8 
  3463                                  readi_buffer:
  3464 0003058C <res 00000200>          	resb 	512
  3465 0003078C <res 00000008>          	resb	8
  3466                                  writei_buffer:
  3467 00030794 <res 00000200>          	resb	512	
  3468                                  ; 24/10/2016
  3469 00030994 <res 00000008>          	resb	8 
  3470                                  rw_buffer:
  3471 0003099C <res 00000800>          	resb 	2048  ; general purposed, r/w sector buffer
  3472                                  
  3473                                  %if 1
  3474                                  ; 28/11/2020
  3475 0003119C <res 00000001>          pmi32:		resb 1	; (>0) use VESA VBE3 protected mode calls 
  3476 0003119D <res 00000001>          vbe_mode_x:	resb 1  ; VESA VBE3 video bios mode set options
  3477 0003119E <res 00000002>          video_mode:	resw 1	; VESA VBE3 video mode (with option flags)  
  3478                                  ; 30/11/2020
  3479 000311A0 <res 00000004>          vbe3bios_addr:	resd 1	; new (writable mem) address of VBE3 bios	
  3480                                  %endif
  3481                                  
  3482                                  %if 1
  3483                                  ; 24/11/2020 - TRDOS 386 v2.0.3
  3484                                  ; BOCHS/PLEX86 VESA VBE3 MODE INFO extension to TRDOS 386 v2 kernel	
  3485                                  MODE_INFO_LIST:
  3486 000311A4 <res 00000044>          	resb	68    ; mode + 66 byte VESA vbe3 mode info (4F01h) 
  3487                                  %endif
  3488                                  
  3489                                  bss_end:
  3490                                  
  3491                                  ; 27/12/2013
  3492                                  _end:  ; end of kernel code
