
=== Trace listing source: srdemss.lst
     1                                  ; SRDISK - EMS memory device driver features control file
     2                                  ; Copyright (C) 1992-1996, 2005 Marko Kohtala
     3                                  ; Released under GNU GPL, read the file 'COPYING' for more information
     4                                  
     5                                  ; EMS 4.0
     6                                  ; Small resident size version
     7                                  
     8                                  ; This is the file to compile.
     9                                  
    10                                  %define MEMORY_STR 'EMS'   ; Define memory type string of any length
    11                                  ;STACKSIZE equ 300       ; Local stack size
    12                                  STACKSIZE equ 0
    13                                  
    14                                  ;=== Push trace listing source: define.mac
    15                                  %include "define.mac" ; NASM included file
     1                              <1> ; SRDISK - device driver definitions
     2                              <1> ; Copyright (c) 1992-1996, 2005 Marko Kohtala
     3                              <1> ; Released under GNU GPL, read the file 'COPYING' for more information
     4                              <1> 
     5                              <1> %define SRD_VERSION     "2.10"      ; FOUR LETTER VERSION STRING
     6                              <1> 
     7                              <1> ; General capabilities in conf.c_flags
     8                              <1> 
     9                              <1> C_APPENDED      equ 1   ; Capable of having appended drivers
    10                              <1> C_MULTIPLE      equ 2   ; Capable of driving many disks
    11                              <1> C_32BITSEC      equ 4   ; Capable of handling over 32-bit sector addresses
    12                              <1> C_NOALLOC       equ 8   ; Incapable of allocating memory by itself
    13                              <1> C_GIOCTL        equ 10h ; Supports Generic IOCTL
    14                              <1> C_DISK_IMAGE    equ 20h ; Can load disk image on startup
    15                              <1> C_UNKNOWN       equ 0C0h
    16                              <1> 
    17                              <1> ; If C_NOALLOC is not set, the malloc field in configuration structure points
    18                              <1> ; into the allocation function. If C_NOALLOC is set, then the malloc
    19                              <1> ; points into the data that SRDISK.EXE needs to be able to handle the memory
    20                              <1> ; by itself.
    21                              <1> 
    22                              <1> ; Boolean
    23                              <1> TRUE    EQU 1
    24                              <1> FALSE   EQU 0
    25                              <1> 
    26                              <1> ; Some important internal settings
    27                              <1> V_FORMAT        equ     1               ; config_s format version used here
    28                              <1> IOCTL_ID        equ     5253h           ; IOCTL write length for call ('SR')
    29                              <1> 
    30                              <1> ;IFNDEF DEBUGGING
    31                              <1> DEBUGGING       equ     FALSE
    32                              <1> ;DEBUGGING       equ     TRUE
    33                              <1> ;ENDIF
    34                              <1> 
    35                              <1> DEBUGINIT       equ     FALSE
    36                              <1> 
    37                              <1> ; disk_IO parameter locations
    38                              <1> labelsize dIO_bytes, word, bp-6     ; May be changed in disk_IO
    39                              <1> labelsize dIO_byteoffset, dword, bp-4    ; May be changed in disk_IO
    40                              <1> labelsize dIO_buffer, dword, bp+6    ; Changed in batch_xfer
    41                              <1> labelsize dIO_sector, dword, bp+10   ; Changed in batch_xfer
    42                              <1> labelsize dIO_count, word, bp+14    ; Changed in batch_xfer
    43                              <1> labelsize dIO_RW, byte, bp+16
    44                              <1> 
    45                              <1> ;******************* Derived definitions ********************
    46                              <1> 
    47                              <1> %if DEBUGGING
    48                              <1> debug   macro char,num
    49                              <1>         push ax
    50                              <1>         push dx
    51                              <1>         IFDIFI <num>,<dx>
    52                              <1>           %IF TYPE num EQ 1
    53                              <1>           xor dh,dh
    54                              <1>           mov dl,[num]
    55                              <1>           %ELSE
    56                              <1>           mov dx,[num]
    57                              <1>           %ENDIF
    58                              <1>         %ENDIF
    59                              <1>         mov al,[char]
    60                              <1>         call debug_c
    61                              <1>         pop dx
    62                              <1>         pop ax
    63                              <1>         endm
    64                              <1> %else
    65                              <1> %macro debug 1+
    66                              <1> %endmacro
    67                              <1> %endif ;DEBUGGING
    68                              <1> 
    69                              <1> 
    16                                  ;=== Pop trace listing source
    17                                  
    18                                  ; What this driver can actually do:
    19                                  ;CAPABLE         equ C_32BITSEC or C_NOALLOC or C_APPENDED or C_GIOCTL
    20                                  CAPABLE         equ C_32BITSEC | C_NOALLOC
    21                                  
    22                                  HOOKINT19       equ     FALSE           ; Hook int 19 if TRUE
    23                                  
    24                                  ;=== Push trace listing source: srdems.mac
    25                                  %include "srdems.mac" ; NASM included file
     1                              <1> ; SRDISK - EMS memory device driver specific code
     2                              <1> ; Copyright (C) 1992-1996, 2005 Marko Kohtala
     3                              <1> ; Released under GNU GPL, read the file 'COPYING' for more information
     4                              <1> 
     5                              <1> ; EMS 4.0
     6                              <1> 
     7                              <1> %define MEMSTR 'EMS '      ; Define 4 char memory type string
     8                              <1> MAX_SIZE equ 7FFFh      ; Maximum possible size
     9                              <1> ALLOCBLOCK equ 16       ; Memory allocation block size
    10                              <1> 
    11                              <1> ;=== Push trace listing source: ems.mac
    12                              <1> %include "ems.mac" ; NASM included file
     1                              <2> ;EMS function codes to be put in AH
     2                              <2> 
     3                              <2> EMS_GET_STATUS          equ 40h
     4                              <2> EMS_FRAME_SEGMENT       equ 41h ; Ret: BX=frame segment
     5                              <2> EMS_FREE_PAGE_COUNT     equ 42h ; Ret: BX=# of unallocated pages
     6                              <2> EMS_ALLOCATE            equ 43h ; BX=Pages, Ret: DX=Handle
     7                              <2> EMS_MAP_HANDLE_PAGES    equ 44h ; AL=Phys page, BX=Log page, DX=Handle
     8                              <2> EMS_DEALLOCATE          equ 45h ; DX=Handle
     9                              <2> EMS_GET_VERSION         equ 46h ; Ret: AL=BCD EMM version
    10                              <2> EMS_SAVE_PMAP           equ 47h ; Save page map
    11                              <2> EMS_RESTORE_PMAP        equ 48h ; Restore page map
    12                              <2> EMS_REALLOCATE_PAGES    equ 51h ; BX=# of pages, DX=handle, Ret: BX=# of pages
    13                              <2> EMS_MOVE_MEM_REGION     equ 57h ; AL=0 (move)/1 (exchange) DS:SI=region
    14                              <2> 
    13                              <1> ;=== Pop trace listing source
    14                              <1> METHOD equ 2
    15                              <1> 
    16                              <1> 
    17                              <1> EMS_block       struc
     0 00000000 ????                    EMS_sizel       dw ?
     0 00000002 ????                    EMS_sizeh       dw ?
     0 00000004 ??                      EMS_stype       db ?
     0 00000005 ????                    EMS_shandle     dw ?
     0 00000007 ????                    EMS_soff        dw ?
     0 00000009 ????                    EMS_spage       dw ?
     0 0000000B ??                      EMS_dtype       db ?
     0 0000000C ????                    EMS_dhandle     dw ?
     0 0000000E ????                    EMS_doff        dw ?
     0 00000010 ????                    EMS_dpage       dw ?
    28                              <1> EMS_block       ends
    29                              <1> 
    30                              <1> EMS_alloc_s struc       ; Changing this structure needs changes in srdisk.exe
     0 00000000 ????                    EMS_handle      dw ? ; -1           ; EMS handle to disk memory (-1=no handle)
     0 00000002 ????                    EMS_frame       dw ?            ; EMS page frame segment
    33                              <1> EMS_cblk: ; NASM structure instance
    34                              <1> EMS_block_size equ EMS_block_struc_size	; NASM port equate
    35                              <1> istruc EMS_block
    36 00000004 <res 12h>           <1> 	resb EMS_block_size
    37                              <1> iend
    38                              <1> EMS_alloc_s ends
    26                                  ;=== Pop trace listing source
    27                                  ;=== Push trace listing source: srdisk.mac
    28                                  %include "srdisk.mac"      ; Create the code itself ; NASM included file
     1                              <1> ;
     2                              <1> ;       ReSizeable RAMDisk device driver
     3                              <1> ;
     4                              <1> ;       Copyright (C) 1992-1996, 2005 Marko Kohtala
     5                              <1> ;       Released under GNU GPL, read the file 'COPYING' for more information
     6                              <1> ;
     7                              <1> ;       To compile with TASM, find the appropriate srd???.asm file and:
     8                              <1> ;               tasm /m2 srd???.asm
     9                              <1> ;               tlink /t srd???.obj,srd???.sys
    10                              <1> 
    11                              <1> [list -]
    16                              <1> [list -]
    18                              <1> [list +]
    19                              <1> 
    20                              <1> %define DR_ATTRIBUTES DHATTR_NOFAT | DHATTR_OPENCLOSE
    21                              <1> 
    22                              <1> %if CAPABLE & C_32BITSEC
    23                              <1> %xdefine DR_ATTRIBUTES DR_ATTRIBUTES | DHATTR_32BIT
    24                              <1> %endif
    25                              <1> 
    26                              <1> %if CAPABLE & C_GIOCTL
    27                              <1> %xdefine DR_ATTRIBUTES DR_ATTRIBUTES | DHATTR_GIOCTL
    28                              <1> %endif
    29                              <1> 
    30                              <1> ;**************************************************************************
    31                              <1> ;
    32                              <1> ;                Device driver start and the structures
    33                              <1> ;
    34                              <1> ;**************************************************************************
    35                              <1> 
=== Switch to base=000000h -> "D_SEG"
    36                              <1> section D_SEG
    37                              <1>                 assume ds:d_seg, cs:d_seg
    38                              <1> 
    39                              <1> ;                org     0
    40                              <1> ; The following is to be considered as both a device driver header and
    41                              <1> ; as a starting point for the configuration table. This driver will be
    42                              <1> ; identified by its segment address and this structure must be at offset
    43                              <1> ; 0.
    44                              <1> 
    45                              <1>                 ; Device driver header
     0 00000000 FFFFFFFF                drhdr_next      dd      -1              ; Pointer to next device (now last)
     0 00000004 0228                    drhdr_attr      dw      DR_ATTRIBUTES
     0 00000006 [1A00]                  drhdr_strategy  dw      j_strategy	; Offset to strategy function
     0 00000008 [1D00]                  drhdr_commands  dw      j_commands	; Offset to commands function
     0 0000000A 01                      drhdr_units     db      1               ; Number of units
    51                              <1> 
    52                              <1> ; The rest has four functions to be considered
    53                              <1> ;  1) usable as device driver name if this driver is changed
    54                              <1> ;     into character device on init.
    55                              <1> ;  2) usable as a label to be returned in media check call
    56                              <1> ;  3) identifies this device driver as SRDISK driver by always having
    57                              <1> ;     the letters SRD at offset dr_ID
    58                              <1> ;  4) identifies the memory used by the 4 char string at offset dr_memory
    59                              <1> 
    60                              <1> dr_volume       label byte
     0 0000000B 535244                  dr_ID           db 'SRD'                ; SRDISK signature (3 char)
     0 0000000E 454D5320                dr_memory       db MEMSTR               ; Memory type identifier (4 char)
     0 00000012 322E3130                dr_version      db SRD_VERSION          ; Device driver version (4 char)
     0 00000016 00                                      db 0                    ; null to end volume label
     0 00000017 01                      dr_v_format     db V_FORMAT             ; Configuration format version
     0 00000018 [2001]                  dr_conf         dw offset conf          ; Pointer to drive configuration
    67                              <1> 
     0 0000001A E9D201                  j_strategy:	fill 3, 90h, jmp strategy
     0 0000001D E9DA01                  j_commands:	jmp commands
    70                              <1> 
    71                              <1> ;**************************************************************************
    72                              <1> ;
    73                              <1> ;               I/O ROUTINE TO THE RAM DISK
    74                              <1> ;
    75                              <1> ; This routine will read a group of sectors inside this part of
    76                              <1> ; the ram disk. If starting sector is not on this part of the disk,
    77                              <1> ; return without error with 0 sectors transferred. If not all sectors
    78                              <1> ; are on this part of the disk, transfer as many as can and report the
    79                              <1> ; number of sectors transferred.
    80                              <1> ;
    81                              <1> ; On entry
    82                              <1> ;   DS:SI - local configuration structure
    83                              <1> ;   dIO_bytes      word ptr [bp-6]   - bytes to move
    84                              <1> ;   dIO_byteoffset (d)word ptr [bp-4]- byte offset of start
    85                              <1> ;   dIO_buffer     dword ptr [bp+6]  - buffer
    86                              <1> ;   dIO_sector     dword ptr [bp+10] - sector
    87                              <1> ;   dIO_count      word ptr [bp+14]  - count
    88                              <1> ;   dIO_RW         byte ptr [bp+16]  - RW (0 = read, nonzero write)
    89                              <1> ;
    90                              <1> ; Preserve
    91                              <1> ;   ds, si, bp and stack contents
    92                              <1> ;
    93                              <1> ; Return
    94                              <1> ;   - carry clear if success
    95                              <1> ;   - carry set on error
    96                              <1> ;
    97                              <1> ;**************************************************************************
    98                              <1> 
    99                              <1> disk_IO         proc far                ; Disk access function
   100                              <1> 
   101                              <1> %if METHOD EQ 1
   102                              <1>                 push si
   103                              <1>                 mov si,offset XMS_alloc + XMS_cblk
   104                              <1>                 mov cx,[dIO_bytes]
   105                              <1>                 mov [si + XMS_sizel],cx
   106                              <1>                 xor cx,cx                       ; cx is zero here
   107                              <1>                 mov [si + XMS_sizeh],cx
   108                              <1> 
   109                              <1>                 les di,[dIO_buffer]
   110                              <1>                 mov ax,word ptr [dIO_byteoffset]
   111                              <1>                 mov dx,word ptr [dIO_byteoffset+2]
   112                              <1>                 mov bx,[XMS_alloc + XMS_handle]
   113                              <1> 
   114                              <1>                 test byte [dIO_RW],-1                  ; Input/output?
   115                              <1>                 jnz @@write
   116                              <1>                                                 ; -- Read
   117                              <1>                 mov [si + XMS_shandle],bx         ; Source in XMS
   118                              <1>                 mov [si + XMS_soffl],ax
   119                              <1>                 mov [si + XMS_soffh],dx
   120                              <1>                 mov [si + XMS_dhandle],cx         ; Destination in main memory
   121                              <1>                 mov [si + XMS_doffl],di
   122                              <1>                 mov [si + XMS_doffh],es
   123                              <1>                 jmp @@move
   124                              <1> @@write:                                          ; -- Write
   125                              <1>                 mov [si + XMS_shandle],cx         ; Destination in main memory
   126                              <1>                 mov [si + XMS_soffl],di
   127                              <1>                 mov [si + XMS_soffh],es
   128                              <1>                 mov [si + XMS_dhandle],bx         ; Source in XMS
   129                              <1>                 mov [si + XMS_doffl],ax
   130                              <1>                 mov [si + XMS_doffh],dx
   131                              <1> @@move:
   132                              <1>                 mov ah,0Bh                      ; Move XMS block
   133                              <1>                 call far [XMS_alloc + XMS_entry]        ; ds:si -> control block
   134                              <1>                 pop si
   135                              <1>                 debug 'X',ax
   136                              <1>                 shr ax,1
   137                              <1>                 cmc                             ; Carry set if err
   138                              <1>                 ret
   139                              <1> %endif
   140                              <1> 
   141                              <1> %if METHOD EQ 2
     0 00000020 56                                      push si
     0 00000021 BE[8A00]                                mov si,offset EMS_alloc + EMS_cblk
     0 00000024 8B4EFA                                  mov cx,[dIO_bytes]
     0 00000027 890C                                    mov [si + EMS_sizel],cx
     0 00000029 31C9                                    xor cx,cx                       ; cx is zero here
     0 0000002B 894C02                                  mov [si + EMS_sizeh],cx
   148                              <1> 
     0 0000002E C47E06                                  les di,[dIO_buffer]
     0 00000031 8B46FC                                  mov ax,word ptr [dIO_byteoffset]
     0 00000034 8B56FE                                  mov dx,word ptr [dIO_byteoffset+2]
     0 00000037 BB0040                                  mov bx,16*1024
     0 0000003A F7F3                                    div bx                          ; ax=page, dx=offset
     0 0000003C 8B1E[8600]                              mov bx,[EMS_alloc + EMS_handle]
   155                              <1> 
     0 00000040 F64610FF                                test byte [dIO_RW],-1                  ; Input/output?
     0 00000044 751B                                    jnz @@write
   158                              <1>                                                 ; -- Read
     0 00000046 C6440401                                mov byte [si + EMS_stype],1            ; Source in EMS
     0 0000004A 895C05                                  mov [si + EMS_shandle],bx
     0 0000004D 895407                                  mov [si + EMS_soff],dx
     0 00000050 894409                                  mov [si + EMS_spage],ax
     0 00000053 884C0B                                  mov [si + EMS_dtype],cl           ; Destination in main memory
     0 00000056 894C0C                                  mov [si + EMS_dhandle],cx
     0 00000059 897C0E                                  mov [si + EMS_doff],di
     0 0000005C 8C4410                                  mov [si + EMS_dpage],es
     0 0000005F EB19                                    jmp @@move
   168                              <1> @@write:                                          ; -- Write
     0 00000061 884C04                                  mov [si + EMS_stype],cl           ; Destination in main memory
     0 00000064 894C05                                  mov [si + EMS_shandle],cx
     0 00000067 897C07                                  mov [si + EMS_soff],di
     0 0000006A 8C4409                                  mov [si + EMS_spage],es
     0 0000006D C6440B01                                mov byte [si + EMS_dtype],1            ; Source in EMS
     0 00000071 895C0C                                  mov [si + EMS_dhandle],bx
     0 00000074 89540E                                  mov [si + EMS_doff],dx
     0 00000077 894410                                  mov [si + EMS_dpage],ax
   177                              <1> @@move:
     0 0000007A B80057                                  mov ax,EMS_MOVE_MEM_REGION * 100h ; Move EMS region
     0 0000007D CD67                                    int 67h                         ; ds:si -> control block
     0 0000007F 5E                                      pop si
   181                              <1>                 debug 'X',ax
     0 00000080 80FC01                                  cmp ah,1                        ; Carry set if err
     0 00000083 F5                                      cmc
     0 00000084 CB                                      ret
   185                              <1> %endif
   186                              <1> 
   187                              <1> %if METHOD EQ 3
   188                              <1>                 push ds
   189                              <1>                 push si
   190                              <1> 
   191                              <1>                 mov dx,[EMS_alloc + EMS_handle]
   192                              <1>                 mov ah,EMS_SAVE_PMAP
   193                              <1>                 int 67h
   194                              <1>                 or ah,ah
   195                              <1>                 jnz @@fail
   196                              <1> 
   197                              <1>                 mov ax,word ptr [dIO_buffer+2]
   198                              <1>                 mov si,word ptr [dIO_buffer]
   199                              <1>                 mov bx,[EMS_alloc + EMS_frame]
   200                              <1>                 cmp byte [dIO_RW],0
   201                              <1>                 jnz @@set_segments
   202                              <1>                   xchg ax,bx
   203                              <1>                   mov di,si
   204                              <1> 
   205                              <1> @@set_segments:   mov ds,ax
   206                              <1>                 mov es,bx
   207                              <1>                 mov bx,-1
   208                              <1>                 assume ds:nothing
   209                              <1> 
   210                              <1>                 ; es:di - target address on disk or memory
   211                              <1>                 ; ds:si - source address on memory or disk
   212                              <1>                 ; bx - last sectors page
   213                              <1> 
   214                              <1> @@next_page:      mov dx,word ptr [dIO_byteoffset+2]
   215                              <1>                 mov ax,word ptr [dIO_byteoffset]
   216                              <1>                 mov cx,16*1024
   217                              <1>                 div cx                          ; ax = page, dx = offset
   218                              <1>                 cmp ax,bx
   219                              <1>                 jz @@move_sector
   220                              <1> 
   221                              <1>                 mov bx,ax                       ; Logical page
   222                              <1>                 cmp byte [dIO_RW],0
   223                              <1>                 jnz @@write
   224                              <1>                 mov si,dx                       ; read, si = offset into page
   225                              <1>                 jmp @@map_page
   226                              <1> @@write:          mov di,dx                       ; @@write, di = offset into page
   227                              <1> @@map_page:       xor al,al                       ; Phys page 0
   228                              <1>                 mov dx,[cs:EMS_alloc + EMS_handle]
   229                              <1>                 mov ah,EMS_MAP_HANDLE_PAGES
   230                              <1>                 int 67h
   231                              <1>                 or ah,ah
   232                              <1>                 jnz @@fail
   233                              <1> 
   234                              <1> @@move_sector:    mov ax,[cs:conf + c_BPB_bps]
   235                              <1>                 mov cx,ax
   236                              <1>                 shr cx,1
   237                              <1>                 rep movsw
   238                              <1>                 sub [dIO_bytes],ax
   239                              <1>                 jbe @@done
   240                              <1> 
   241                              <1>                 add word ptr [dIO_byteoffset],ax
   242                              <1>                 adc word [dIO_byteoffset+2],0
   243                              <1>                 jmp @@next_page
   244                              <1> 
   245                              <1> @@fail:           stc
   246                              <1>                 jmp @@finnish
   247                              <1> 
   248                              <1> @@done:           clc
   249                              <1> @@finnish:
   250                              <1>                 pushf
   251                              <1>                 mov dx,[cs:EMS_alloc + EMS_handle]
   252                              <1>                 mov ah,EMS_RESTORE_PMAP
   253                              <1>                 int 67h
   254                              <1> ;                cmp ah,1 ; Set carry if nonzero
   255                              <1> ;                cmc
   256                              <1>                 popf
   257                              <1>                 pop si
   258                              <1>                 pop ds
   259                              <1>                 ret
   260                              <1> 
   261                              <1>                 assume ds:d_seg
   262                              <1> %endif
   263                              <1> 
   264                              <1> disk_IO         endp
   265                              <1> 
   266                              <1> %ifn CAPABLE & C_NOALLOC
   267                              <1> 
   268                              <1> ;**************************************************************************
   269                              <1> ;
   270                              <1> ;               EXTERNAL MEMORY ALLOCATION ROUTINE
   271                              <1> ;
   272                              <1> ; This routine is only used if CAPABLE has C_NOALLOC bit clear.
   273                              <1> ;
   274                              <1> ; Allocate requested amount of memory. If memory is available in chunks,
   275                              <1> ; the amount can be rounded up. If not enough memory available, allocate
   276                              <1> ; as much as possible or just report the amount that was previously
   277                              <1> ; allocated. It is expected that at least as much memory can be allocated
   278                              <1> ; as there previously was. Reallocation should not destroy memory
   279                              <1> ; contents - it is essential to be able to resize a disk without losing
   280                              <1> ; the contents.
   281                              <1> ;
   282                              <1> ; On entry
   283                              <1> ;   DWORD [sp+4] - Kbytes to allocate
   284                              <1> ;
   285                              <1> ; Preserve
   286                              <1> ;   es, ds
   287                              <1> ;   si, di
   288                              <1> ;
   289                              <1> ; Return dx:ax = Kbytes allocated
   290                              <1> ;
   291                              <1> ;**************************************************************************
   292                              <1> 
   293                              <1> malloc          proc far              ; Memory allocation function
   294                              <1> 
   295                              <1>  %if 0
   296                              <1>                 arg kbytes:dword
   297                              <1>  %endif
   298                              <1> 	lframe far
   299                              <1> 	lpar dword, kbytes
   300                              <1> 	%xdefine kbytes bp + ?kbytes
   301                              <1> 	lenter
   302                              <1> 
   303                              <1> %if METHOD EQ 1
   304                              <1>                 assume ds:nothing
   305                              <1>                 test word [kbytes+2],-1       ; Over 0FFFFh K is impossible
   306                              <1>                 jnz @@fail
   307                              <1>                 mov bx,word ptr [kbytes]          ; New disk size
   308                              <1>                 mov dx,[cs:XMS_alloc + XMS_handle]     ; Handle to the memory
   309                              <1>                 mov ah,0Fh                      ; Reallocate
   310                              <1>                 or dx,dx
   311                              <1>                 jnz @@alloc                       ; If no handle, then
   312                              <1>                   mov dx,bx                     ; allocate
   313                              <1>                   mov ah,9
   314                              <1> @@alloc:
   315                              <1>                 call far [cs:XMS_alloc + XMS_entry]
   316                              <1>                 or ax,ax
   317                              <1>                 jnz @@ok
   318                              <1> 
   319                              <1> @@fail:           mov ax,word ptr [cs:conf + c_size]     ; Fail, return current
   320                              <1>                 xor dx,dx
   321                              <1> 	lleave code
   322                              <1>                 ret
   323                              <1> 
   324                              <1> @@ok:             mov ax,word ptr [kbytes]          ; Ok, return requested
   325                              <1>                 xor dx,dx
   326                              <1> 	lleave code
   327                              <1>                 ret
   328                              <1>                 assume ds:d_seg
   329                              <1> %endif
   330                              <1> 
   331                              <1> %if METHOD EQ 2
   332                              <1>                 assume ds:nothing
   333                              <1> 
   334                              <1>                 mov ax,word ptr [kbytes]          ; New disk size
   335                              <1>                 mov dx,word ptr [kbytes+2]
   336                              <1>                 cmp dx,15*1024
   337                              <1>                 jae @@fail
   338                              <1> 
   339                              <1>                 mov cx,16*1024
   340                              <1>                 div cx
   341                              <1>                 or dx,dx
   342                              <1>                 jz @@no_roundup
   343                              <1>                   inc ax
   344                              <1> @@no_roundup:     mov bx,ax
   345                              <1>                 mov dx,[cs:EMS_alloc + EMS_handle]     ; Handle to the memory
   346                              <1>                 or ax,ax
   347                              <1>                 jz free
   348                              <1>                 cmp dx,-1                       ; Is the handle valid?
   349                              <1>                 jne @@realloc
   350                              <1>                   mov ah,EMS_ALLOCATE
   351                              <1>                   int 67h
   352                              <1>                   or ah,ah
   353                              <1>                   jnz @@fail
   354                              <1>                   mov [cs:EMS_alloc + EMS_handle],dx
   355                              <1>                   jmp @@ok
   356                              <1> free:
   357                              <1>                 mov ah,EMS_DEALLOCATE
   358                              <1>                 int 67h
   359                              <1>                 or ah,ah
   360                              <1>                 jnz @@fail
   361                              <1>                 mov [cs:EMS_alloc + EMS_handle],dx
   362                              <1>                 jmp @@ok
   363                              <1> @@realloc:
   364                              <1>                 mov ah,EMS_REALLOCATE_PAGES     ; Reallocate
   365                              <1>                 int 67h
   366                              <1>                 or ah,ah
   367                              <1>                 jnz @@fail
   368                              <1> 
   369                              <1> @@ok:             mov ax,word ptr [kbytes]          ; Ok, return requested
   370                              <1>                 xor dx,dx
   371                              <1> 	lleave code
   372                              <1>                 ret
   373                              <1> 
   374                              <1> @@fail:           mov ax,word ptr [cs:conf + c_size]     ; Fail, return current
   375                              <1>                 xor dx,dx
   376                              <1> 	lleave code
   377                              <1>                 ret
   378                              <1> 
   379                              <1>                 assume ds:d_seg
   380                              <1> %endif
   381                              <1> 
   382                              <1> %if METHOD EQ 3
   383                              <1>                 assume ds:nothing
   384                              <1> 
   385                              <1>                 mov ax,word ptr [kbytes]          ; New disk size
   386                              <1>                 mov dx,word ptr [kbytes+2]
   387                              <1>                 cmp dx,15*1024
   388                              <1>                 jae @@fail
   389                              <1> 
   390                              <1>                 mov cx,16*1024
   391                              <1>                 div cx
   392                              <1>                 or dx,dx
   393                              <1>                 jz @@no_roundup
   394                              <1>                   inc ax
   395                              <1> @@no_roundup:     mov bx,ax
   396                              <1>                 mov dx,[cs:EMS_alloc + EMS_handle]     ; Handle to the memory
   397                              <1>                 or ax,ax
   398                              <1>                 jz @@free
   399                              <1>                 cmp dx,-1                       ; Is the handle valid?
   400                              <1>                 jne @@realloc
   401                              <1>                   mov ah,EMS_ALLOCATE
   402                              <1>                   int 67h
   403                              <1>                   or ah,ah
   404                              <1>                   jnz @@fail
   405                              <1>                   mov [cs:EMS_alloc + EMS_handle],dx
   406                              <1>                   jmp @@ok
   407                              <1> @@free:
   408                              <1>                 mov ah,EMS_DEALLOCATE
   409                              <1>                 int 67h
   410                              <1>                 or ah,ah
   411                              <1>                 jnz @@fail
   412                              <1>                 mov [cs:EMS_alloc + EMS_handle],dx
   413                              <1>                 jmp @@ok
   414                              <1> @@realloc:                                        ; !!!! Not a 3.2 call!
   415                              <1>                 mov ah,EMS_REALLOCATE_PAGES     ; Reallocate
   416                              <1>                 int 67h
   417                              <1>                 or ah,ah
   418                              <1>                 jnz @@fail
   419                              <1> 
   420                              <1> @@ok:             mov ax,word ptr [kbytes]          ; Ok, return requested
   421                              <1>                 xor dx,dx
   422                              <1> 	lleave code
   423                              <1>                 ret
   424                              <1> 
   425                              <1> @@fail:           mov ax,word ptr [cs:conf + c_size]     ; Fail, return current
   426                              <1>                 xor dx,dx
   427                              <1> 	lleave code
   428                              <1>                 ret
   429                              <1> 
   430                              <1>                 assume ds:d_seg
   431                              <1> %endif
   432                              <1> 	%undef kbytes
   433                              <1> 	lleave ctx
   434                              <1> 
   435                              <1> malloc          endp
   436                              <1> 
   437                              <1> ;**************************************************************************
   438                              <1> ;
   439                              <1> ;               QUERY FREE MEMORY
   440                              <1> ;
   441                              <1> ; This routine is only used if CAPABLE has C_NOALLOC bit clear.
   442                              <1> ;
   443                              <1> ; On entry
   444                              <1> ;
   445                              <1> ; Preserve
   446                              <1> ;   ds, si, di, bp and stack contents
   447                              <1> ;
   448                              <1> ; Return
   449                              <1> ;   - dx:ax set to maximum safe size to reallocate to
   450                              <1> ;   - cx:bx set to maximum size to reallocate to (may not be valid)
   451                              <1> ;
   452                              <1> ;**************************************************************************
   453                              <1> 
   454                              <1> freemem         proc far
   455                              <1> 
   456                              <1> %if METHOD EQ 1
   457                              <1>                 assume ds:nothing
   458                              <1>                 mov ah,8
   459                              <1>                 call far [cs:XMS_alloc + XMS_entry]
   460                              <1>                 xor dx,dx
   461                              <1>                 mov bx,ax
   462                              <1>                 mov cx,dx
   463                              <1>                 add bx,word ptr [conf.size]
   464                              <1>                 adc cx,word ptr [conf.size+2]
   465                              <1>                 ret
   466                              <1>                 assume ds:d_seg
   467                              <1> %endif
   468                              <1> 
   469                              <1> %if METHOD EQ 2
   470                              <1>                 assume ds:nothing
   471                              <1>                 mov ah,EMS_FREE_PAGE_COUNT
   472                              <1>                 int 67h                 ; bx = unallocated pages
   473                              <1>                 mov ax,16               ; of 16K each
   474                              <1>                 mul bx                  ; dx:ax = total free K
   475                              <1>                 add ax,word ptr [conf.size]
   476                              <1>                 adc dx,word ptr [conf.size+2]
   477                              <1>                 mov bx,ax
   478                              <1>                 mov cx,dx
   479                              <1>                 ret
   480                              <1>                 assume ds:d_seg
   481                              <1> %endif
   482                              <1> 
   483                              <1> %if METHOD EQ 3
   484                              <1>                 assume ds:nothing
   485                              <1>                 mov ah,EMS_FREE_PAGE_COUNT
   486                              <1>                 int 67h                 ; bx = unallocated pages
   487                              <1>                 mov ax,16               ; of 16K each
   488                              <1>                 mul bx                  ; dx:ax = total free K
   489                              <1>                 add ax,word ptr [conf.size]
   490                              <1>                 adc dx,word ptr [conf.size+2]
   491                              <1>                 mov bx,ax
   492                              <1>                 mov cx,dx
   493                              <1>                 ret
   494                              <1>                 assume ds:d_seg
   495                              <1> %endif
   496                              <1> 
   497                              <1> freemem         endp
   498                              <1> 
   499                              <1> %else    ; ife CAPABLE and C_NOALLOC
   500                              <1> 
   501                              <1> freemem equ 0
   502                              <1> %endif   ; ife CAPABLE and C_NOALLOC
   503                              <1> 
   504                              <1> ret_far proc far                        ; Null function to replace
     0 00000085 CB                              ret                             ;  strategy and command when appended
   506                              <1> ret_far endp                            ;  to another SRDISK drive
   507                              <1> 
   508                              <1> %if HOOKINT19
   509                              <1> 
   510                              <1> ;**************************************************************************
   511                              <1> ;
   512                              <1> ;                       Warm Boot of Machine
   513                              <1> ;
   514                              <1> ; Release used XMS memory on warm boot.
   515                              <1> ;
   516                              <1> ; I guess this may be important if some virtual machine (VM) in some
   517                              <1> ; multitasking system has installed this driver and the VM is ended.
   518                              <1> ; Without this the other VMs could lose the space reserved for RAM disk
   519                              <1> ; in this VM.
   520                              <1> ;**************************************************************************
   521                              <1> 
   522                              <1> iispentry int_19_entry		; INT 19 boot function
   523                              <1> old_int19: equ .next
   524                              <1> 
   525                              <1> %if METHOD EQ 1
   526                              <1>                 assume ds:nothing
   527                              <1>                 push ax
   528                              <1>                 push bx
   529                              <1>                 push dx
   530                              <1>                 push ds
   531                              <1>                 pushf
   532                              <1>                 mov     dx,[cs:XMS_alloc + XMS_handle]
   533                              <1>                 test    dx,dx
   534                              <1>                 jz      @@int19_1                 ; Jump if no XMS handle
   535                              <1> 		mov	ah,0Ah
   536                              <1>                 call    far [cs:XMS_alloc + XMS_entry]     ; Free XMS memory
   537                              <1> @@int19_1:
   538                              <1>                 xor     ax,ax
   539                              <1>                 mov     word [cs:XMS_alloc + XMS_handle], ax
   540                              <1> 		mov	ds,ax
   541                              <1>                 mov     ax,[cs:old_int19 + 0]
   542                              <1> 		cli				; Disable interrupts
   543                              <1>                 mov     [19h*4],ax           ; for the time to write
   544                              <1>                 mov     ax,[cs:old_int19 + 2]        ; old interrupt vector back
   545                              <1>                 mov     [19h*4+2],ax
   546                              <1>                 popf
   547                              <1>                 pop ds
   548                              <1>                 pop dx
   549                              <1>                 pop bx
   550                              <1>                 pop ax
   551                              <1>                 jmp     far [cs:old_int19]
   552                              <1>                 assume ds:d_seg
   553                              <1> %endif
   554                              <1> 
   555                              <1> %if METHOD EQ 2
   556                              <1>                 assume ds:nothing
   557                              <1>                 push ax
   558                              <1>                 push dx
   559                              <1>                 push ds
   560                              <1>                 pushf
   561                              <1>                 mov dx,[cs:EMS_alloc + XMS_handle]
   562                              <1>                 cmp dx,-1
   563                              <1>                 jne @@int19_1                     ; Jump if no EMS handle
   564                              <1>                 mov ah,EMS_DEALLOCATE
   565                              <1>                 int 67h                         ; Free EMS memory
   566                              <1>                 or word [cs:EMS_alloc + EMS_handle],-1
   567                              <1> @@int19_1:
   568                              <1>                 xor ax,ax
   569                              <1>                 mov ds,ax
   570                              <1>                 mov ax,[cs:old_int19 + 0]
   571                              <1> 		cli				; Disable interrupts
   572                              <1>                 mov [19h*4],ax               ; for the time to write
   573                              <1>                 mov ax,[cs:old_int19 + 2]            ; old interrupt vector back
   574                              <1>                 mov [19h*4+2],ax
   575                              <1>                 popf
   576                              <1>                 pop ds
   577                              <1>                 pop dx
   578                              <1>                 pop ax
   579                              <1>                 jmp far [cs:old_int19]
   580                              <1>                 assume ds:d_seg
   581                              <1> %endif
   582                              <1> 
   583                              <1> %if METHOD EQ 3
   584                              <1>                 assume ds:nothing
   585                              <1>                 push ax
   586                              <1>                 push dx
   587                              <1>                 push ds
   588                              <1>                 pushf
   589                              <1>                 mov dx,[cs:EMS_alloc + XMS_handle]
   590                              <1>                 cmp dx,-1
   591                              <1>                 jne @@int19_1                     ; Jump if no EMS handle
   592                              <1>                 mov ah,EMS_DEALLOCATE
   593                              <1>                 int 67h                         ; Free EMS memory
   594                              <1>                 or word [cs:EMS_alloc + EMS_handle],-1
   595                              <1> @@int19_1:
   596                              <1>                 xor ax,ax
   597                              <1>                 mov ds,ax
   598                              <1>                 mov ax,[cs:old_int19 + 0]
   599                              <1> 		cli				; Disable interrupts
   600                              <1>                 mov [19h*4],ax               ; for the time to write
   601                              <1>                 mov ax,[cs:old_int19 + 2]            ; old interrupt vector back
   602                              <1>                 mov [19h*4+2],ax
   603                              <1>                 popf
   604                              <1>                 pop ds
   605                              <1>                 pop dx
   606                              <1>                 pop ax
   607                              <1>                 jmp far [cs:old_int19]
   608                              <1>                 assume ds:d_seg
   609                              <1> %endif
   610                              <1> 
   611                              <1> int_19_entry    endp
   612                              <1> %endif   ; HOOKINT19
   613                              <1> 
   614                              <1>                       ; Memory specific resident data
   615                              <1> ;**************************************************************************
   616                              <1> ;
   617                              <1> ;                       Local data
   618                              <1> ;
   619                              <1> ; This data is used by the two above routines that are needed
   620                              <1> ; resident in any case.
   621                              <1> ;
   622                              <1> ;**************************************************************************
   623                              <1> 
   624                              <1> %if METHOD EQ 1
   625                              <1> XMS_alloc: ; NASM structure instance
   626                              <1> XMS_alloc_s_size equ XMS_alloc_s_struc_size	; NASM port equate
   627                              <1> istruc XMS_alloc_s
   628                              <1> iend
   629                              <1> 
   630                              <1> %if CAPABLE & C_NOALLOC
   631                              <1> malloc EQU offset XMS_alloc
   632                              <1> %endif
   633                              <1> %endif
   634                              <1> 
   635                              <1> %if METHOD EQ 2
   636                              <1> EMS_alloc: ; NASM structure instance
   637                              <1> EMS_alloc_s_size equ EMS_alloc_s_struc_size	; NASM port equate
   638                              <1> istruc EMS_alloc_s
     0 00000086 FFFF                    at EMS_handle,	dw -1
     0 00000088 00<rep 14h>             iend
   641                              <1> 
   642                              <1> %if CAPABLE & C_NOALLOC
   643                              <1> malloc EQU offset EMS_alloc
   644                              <1> %endif
   645                              <1> %endif
   646                              <1> 
   647                              <1> %if METHOD EQ 3
   648                              <1> EMS_alloc: ; NASM structure instance
   649                              <1> EMS_alloc_s_size equ EMS_alloc_s_struc_size	; NASM port equate
   650                              <1> istruc EMS_alloc_s
   651                              <1> at EMS_handle,	dw -1
   652                              <1> iend
   653                              <1> 
   654                              <1> %if CAPABLE & C_NOALLOC
   655                              <1> malloc EQU offset EMS_alloc
   656                              <1> %endif
   657                              <1> %endif
   658                              <1> 
   659                              <1> 
   660                              <1> ;**************************************************************************
   661                              <1> ;
   662                              <1> ;                       Debugging code
   663                              <1> ;
   664                              <1> ; This code prints out a character and a word in hex. This code can be
   665                              <1> ; used using "debug char,word" macro in the code to give some output of
   666                              <1> ; the actions device driver is doing.
   667                              <1> ;
   668                              <1> ; A color display is assumed with 80 characters on a row and 25 rows.
   669                              <1> ;
   670                              <1> ;**************************************************************************
   671                              <1> 
   672                              <1> %if DEBUGGING
   673                              <1>                 assume ds:nothing
   674                              <1> 
   675                              <1> debug_c         proc near
   676                              <1>                 push es
   677                              <1>                 push di
   678                              <1> 
   679                              <1>                 mov ah,[cs:d_attr]           ; Load color attribute
   680                              <1>                 mov di,0B800h           ; Load screen segment (assumes color)
   681                              <1>                 mov es,di
   682                              <1>                 mov di,[cs:d_loc]            ; Load line
   683                              <1>                 cmp di,26*160           ; Below screen?
   684                              <1>                 jb debug_c1
   685                              <1>                   mov di,2*160          ; Yes, move to third line (for scroll off)
   686                              <1>                   mov [cs:d_loc],di
   687                              <1>                   add ah,10h            ; Change color
   688                              <1>                   cmp ah,70h
   689                              <1>                   jb debug_c2
   690                              <1>                     sub ah,60h
   691                              <1> debug_c2:         mov [cs:d_attr],ah
   692                              <1> 
   693                              <1>                   push es               ; Wait if shift down
   694                              <1>                   push ax
   695                              <1>                   mov ax,40h
   696                              <1>                   mov es,ax
   697                              <1> debug_c3:         test byte ptr [es:17h],3
   698                              <1>                   jnz debug_c3
   699                              <1>                   pop ax
   700                              <1>                   pop es
   701                              <1> debug_c1:
   702                              <1>                 add di,[cs:d_col]            ; Advance to right column
   703                              <1>                 mov [es:di],ax          ; Print error letter
   704                              <1> 
   705                              <1>                 call debug_x            ; Print high byte
   706                              <1>                 mov dh,dl
   707                              <1>                 call debug_x            ; Print low byte
   708                              <1> 
   709                              <1>                 add word [cs:d_loc],160           ; Next line
   710                              <1> 
   711                              <1>                 pop di
   712                              <1>                 pop es
   713                              <1>                 ret
   714                              <1> debug_c         endp
   715                              <1> 
   716                              <1> debug_x         proc near               ; Print a byte in hex
   717                              <1>                 mov al,dh
   718                              <1>                 shr al,1
   719                              <1>                 shr al,1
   720                              <1>                 shr al,1
   721                              <1>                 shr al,1
   722                              <1>                 call debug_x1
   723                              <1>                 mov al,dh
   724                              <1> debug_x1:       and al,0Fh              ; Print a hex digit
   725                              <1>                 cmp al,10
   726                              <1>                 jae debug_x2
   727                              <1>                   add al,'0'
   728                              <1>                   jmp debug_x3
   729                              <1> debug_x2:       add al,'A'-10
   730                              <1> debug_x3:
   731                              <1>                 inc di
   732                              <1>                 inc di
   733                              <1>                 mov [es:di],ax
   734                              <1>                 ret
   735                              <1> debug_x         endp
   736                              <1> 
   737                              <1> d_loc   dw 2*160
   738                              <1> d_col   dw 150
   739                              <1> d_attr  db 40h
   740                              <1> 
   741                              <1>                 assume ds:d_seg
   742                              <1> 
   743                              <1> %endif ; DEBUGGING
   744                              <1> 
   745                              <1> 
   746                              <1> 	align 2, db 0
     0 0000009C 00000000                ctrl0:		dd 0			; far pointer to first driver
   748                              <1> 	; This is initialised from int 2Dh, except if no prior
   749                              <1> 	;  driver is resident. In the latter case, it is made to
   750                              <1> 	;  point to this driver instance itself.
   751                              <1> 	; We don't use a reference to an AMIS multiplex number
   752                              <1> 	;  because those can change from the renumber utility.
   753                              <1> 	; If we add uninstall support, then the ctrl0 of all
   754                              <1> 	;  remaining resident instances must be updated so they
   755                              <1> 	;  no longer point to an about to be uninstalled instance.
   756                              <1> 
   757                              <1> amis_sign:
     0 000000A0 65636D20<rep 5h>        	fill 8, 32, db "ecm"
     0 000000A8 53524449534B20          	fill 8, 32, db "SRDISK"
   759 000000A8 <rep 2h>            <1> 
     0 000000B0 726553697A6561626C      	asciz "reSizeable RAM Disk"
     0 000000B9 652052414D20446973
     0 000000C2 6B00
   761                              <1> 
   762                              <1> intlist:
   763                              <1> %if HOOKINT19
   764                              <1> 	db 19h
   765                              <1> 	dw int_19_entry
   766                              <1> %endif
     0 000000C4 2D                      	db 2Dh
     0 000000C5 [C800]                  	dw i2D
   769                              <1> 
     0 000000C7 CBEB10000000004B42      iispentry i2D
   770 000000D0 00EBF400<rep 7h>    <1> 
     0 000000DA 80FC00                  	cmp ah, 0
   772                              <1> .multiplexnumber: equ $ - 1
     0 000000DD 7405                    	je .ours
     0 000000DF 2EFF2E[CA00]            	jmp far [cs:.next]
   775                              <1> 
   776                              <1> .ours:
     0 000000E4 3C00                    	cmp al, 0
     0 000000E6 7413                    	je .installed
     0 000000E8 3C04                    	cmp al, 4
     0 000000EA 741A                    	je .intlist
     0 000000EC 3C06                    	cmp al, 6
     0 000000EE 741B                    	je .device
     0 000000F0 3C10                    	cmp al, 10h
     0 000000F2 741E                    	je .getcompatible
     0 000000F4 3C20                    	cmp al, 20h
     0 000000F6 7420                    	je .ctrl0
     0 000000F8 B000                    	mov al, 0
     0 000000FA CF                      	iret
   789                              <1> 
   790                              <1> .installed:
     0 000000FB B90A02                  	mov cx, 200h + 10		; v2.10
     0 000000FE BF[A000]                	mov di, amis_sign
   793                              <1> .iret_dx_al:
     0 00000101 B0FF                    	mov al, -1
   795                              <1> .iret_dx:
     0 00000103 8CCA                    	mov dx, cs
     0 00000105 CF                      	iret
   798                              <1> 
   799                              <1> .intlist:				; al == 04h already
     0 00000106 BB[C400]                	mov bx, intlist
     0 00000109 EBF8                    	jmp .iret_dx
   802                              <1> 
   803                              <1> .device:
     0 0000010B B80101                  	mov ax, 0101h			; ah = flags
   805                              <1> 		; (loaded from config, linked into chain, inreentrant)
   806                              <1> 					; al = number of headers
     0 0000010E 31DB                    	xor bx, bx
     0 00000110 EBF1                    	jmp .iret_dx			; dx:bx -> header
   809                              <1> 
   810                              <1> .getcompatible:
     0 00000112 B0FF                    	mov al, -1
     0 00000114 B90A02                  	mov cx, 200h + 10		; v2.10
     0 00000117 CF                      	iret
   814                              <1> 
   815                              <1> .ctrl0:
     0 00000118 B004                    	mov al, 4
     0 0000011A BB[9C00]                	mov bx, ctrl0
     0 0000011D EBE4                    	jmp .iret_dx
   819                              <1> 
   820                              <1> 
   821                              <1> ;**************************************************************************
   822                              <1> ;
   823                              <1> ;                       Configuration tables
   824                              <1> ;
   825                              <1> ; This structure holds all the formatting data used by the formatter.
   826                              <1> ; The formatter is passed a pointer to this data and it modifies it
   827                              <1> ; directly. For this arrangement to work THE BELOW TABLE MAY NOT BE
   828                              <1> ; MODIFIED WITHOUT PROPER CHANGES IN SRDISK.EXE. dr_v_format contains
   829                              <1> ; version number which is to be changed when a change is made to this
   830                              <1> ; structure.
   831                              <1> ;
   832                              <1> ; Only the first fields up to label appended_eor is resident and used in
   833                              <1> ; in every case. The rest is used only in the main driver in a chain of
   834                              <1> ; RAM disk drivers.
   835                              <1> ;
   836                              <1> ; !!! The formatter may use any initial values in this structure as
   837                              <1> ;     default values i.e. set all needed values here !!!
   838                              <1> ; !!! A DR-DOS bug must be avoided by defining c_BPB_sectors and
   839                              <1> ;     c_BPB_FATsectors so that they could be real !!!
   840                              <1> ;**************************************************************************
   841                              <1> 
   842                              <1> READ_ACCESS     equ     1       ; Bit masks for the RW_access
   843                              <1> WRITE_ACCESS    equ     2
   844                              <1> 
   845                              <1> config_s struc
     0 00000000 ??                      c_drive         db      ?               ; Drive letter
     0 00000001 ??                      c_flags         db      ? ; CAPABLE         ; Misc capability flags
     0 00000002 ????                    c_disk_IO       dw      ? ; offset disk_IO  ; disk_IO entry
     0 00000004 ????                    c_disk_IO_seg   dw      ? ; 0               ; disk_IO entry segment
     0 00000006 ????                    c_malloc        dw      ? ; malloc          ; malloc entry offset (in DS/CS)
     0 00000008 ????                    c_freemem       dw      ? ; freemem         ; free mem query entry offset (in DS/CS)
     0 0000000A ????                    c_next          dw      ? ; 0               ; Next driver in chain (segment)
     0 0000000C ????????                c_maxK          dd      ? ; MAX_SIZE        ; Maximum allowed size
     0 00000010 ????????                c_size          dd      ? ; 0               ; Current allocated size in Kbytes
     0 00000014 ????                    c_allocblock    dw      ? ; ALLOCBLOCK      ; Memory allocation block size
     0 00000016 ????                    c_sectorsl      dw      ? ; 0               ; Sectors in this driver (low word)
     0 00000018 ????                    c_sectorsh      dw      ? ; 0               ; Sectors in this driver (high word)
     0 0000001A ??                      c_bps_shift     db      ? ; 7               ; 2^c_bps_shift == c_BPB_bps
   859                              <1> 
     0 0000001B ????                    c_BPB_bps       dw      ? ; 512             ; Sector size
     0 0000001D ??                      c_BPB_spc       db      ? ; 1               ; Cluster size in sectors
     0 0000001E ????                    c_BPB_reserved  dw      ? ; 1               ; The boot sector is reserved
     0 00000020 ??                      c_BPB_FATs      db      ? ; 1               ; One FAT copy
     0 00000021 ????                    c_BPB_dir       dw      ? ; 64              ; 64 entries in root directory
     0 00000023 ????                    c_BPB_sectors   dw      ? ; 100             ; number of sectors on 16-bit disk
     0 00000025 ??                      c_BPB_media     db      ? ; 0FAh            ; Media is RAM DISK
     0 00000026 ????                    c_BPB_FATsectors dw     ? ; 1               ; Sectors per one FAT
     0 00000028 ????                    c_BPB_spt       dw      ? ; 8               ; Sectors per track
     0 0000002A ????                    c_BPB_heads     dw      ? ; 1               ; Number of heads
     0 0000002C ????                    c_BPB_hiddenl   dw      ? ; 0               ; # of hidden sectors (low word)
     0 0000002E ????                    c_BPB_hiddenh   dw      ? ; 0               ; # of hidden sectors (high word)
     0 00000030 ????                    c_BPB_tsectorsl dw      ? ; 0               ; # of sectors on 32-bit disk (low word)
     0 00000032 ????                    c_BPB_tsectorsh dw      ? ; 0               ; # of sectors on 32-bit disk (high)
   874                              <1> 
     0 00000034 ????????                c_tsize         dd      ? ; 0               ; Total size in Kbytes (all drivers)
   876                              <1> 
     0 00000038 ??                      c_RW_access     db      ? ; 000b            ; B0 = read, B1 = write, B2 = fixed
     0 00000039 ??                      c_media_change  db      ? ; 1               ; -1 if media changed, 1 if not
     0 0000003A ??                      c_device_type   db      ? ; 0               ; Device type for Generic IOCTL
     0 0000003B ????                    c_open_files    dw      ? ; 0               ; Files currently open on drive
     0 0000003D ????                    c_next_drive    dw      ? ; 0               ; Segment of next SRDISK drive
     0 0000003F ????                    c_transfer      dw      ? ; batch_xfer      ; Batch xfer function address
   883                              <1> config_s ends
   884                              <1> 
     0 0000011F 00                      	align 2, db 0
   886                              <1> ;conf            config_s <>
   887                              <1> ; TASM 3.0 bugs force this approach:
   888                              <1> conf: ; NASM structure instance
   889                              <1> config_s_size equ config_s_struc_size	; NASM port equate
   890                              <1> istruc config_s
   891                              <1> at c_drive
     0 00000120 00                      	db 0
   893                              <1> at c_flags
     0 00000121 0C                      	db CAPABLE
   895                              <1> at c_disk_IO
     0 00000122 [2000]                  	dw offset disk_IO
   897                              <1> at c_disk_IO_seg
     0 00000124 0000                    	dw 0
   899                              <1> at c_malloc
     0 00000126 [8600]                  	dw malloc
   901                              <1> at c_freemem
     0 00000128 0000                    	dw freemem
   903                              <1> at c_next
     0 0000012A 0000                    	dw 0
   905                              <1> at c_maxK
     0 0000012C FF7F0000                	dd MAX_SIZE
   907                              <1> at c_size
     0 00000130 00000000                	dd 0
   909                              <1> at c_allocblock
     0 00000134 1000                    	dw ALLOCBLOCK
   911                              <1> at c_sectorsl
     0 00000136 0000                    	dw 0
   913                              <1> at c_sectorsh
     0 00000138 0000                    	dw 0
   915                              <1> at c_bps_shift
     0 0000013A 09                      	db 9
   917                              <1> at c_BPB_bps
     0 0000013B 0002                    	dw 512
   919                              <1> at c_BPB_spc
     0 0000013D 01                      	db 1
   921                              <1> at c_BPB_reserved
     0 0000013E 0100                    	dw 1
   923                              <1> at c_BPB_FATs
     0 00000140 01                      	db 1
   925                              <1> at c_BPB_dir
     0 00000141 4000                    	dw 64
   927                              <1> at c_BPB_sectors
     0 00000143 6400                    	dw 100
   929                              <1> at c_BPB_media
     0 00000145 FA                      	db 0FAh
   931                              <1> at c_BPB_FATsectors
     0 00000146 0100                    	dw 1
   933                              <1> at c_BPB_spt
     0 00000148 0800                    	dw 8
   935                              <1> at c_BPB_heads
     0 0000014A 0100                    	dw 1
   937                              <1> at c_BPB_hiddenl
     0 0000014C 0000                    	dw 0
   939                              <1> at c_BPB_hiddenh
     0 0000014E 0000                    	dw 0
   941                              <1> at c_BPB_tsectorsl
     0 00000150 0000                    	dw 0
   943                              <1> at c_BPB_tsectorsh
     0 00000152 0000                    	dw 0
   945                              <1> at c_tsize
     0 00000154 00000000                	dd 0
   947                              <1> at c_RW_access
     0 00000158 00                      	db 0
   949                              <1> at c_media_change
     0 00000159 01                      	db 1
   951                              <1> at c_device_type
     0 0000015A 00                      	db 0
   953                              <1> at c_open_files
     0 0000015B 0000                    	dw 0
   955                              <1> at c_next_drive
     0 0000015D 0000                    	dw 0
   957                              <1> at c_transfer
     0 0000015F [8901]                  	dw batch_xfer
   959                              <1> iend
   960                              <1> 
   961                              <1> appended_eor    equ offset conf + c_BPB_spc ; End of resident for appended driver
   962                              <1> 
   963                              <1> 
   964                              <1> ;**************************************************************************
   965                              <1> ;
   966                              <1> ;               Other internal and resident data
   967                              <1> ;
   968                              <1> ; The order of this data is not significant as it will not be used outside
   969                              <1> ;
   970                              <1> ;**************************************************************************
   971                              <1> 
     0 00000161 00                      	align 2, db 0
   973                              <1> labelsize BPB, byte, conf + c_BPB_bps
     0 00000162 [3B01]                  pBPB            dw offset BPB           ; Pointer to BPB (for cmd_init)
   975                              <1> 
     0 00000164 00000000                req_ptr         dd 0                    ; Request structure pointer
   977                              <1> 
   978                              <1> %if STACKSIZE
   979                              <1> caller_sp       dw 0                    ; To store pointer to callers stack
   980                              <1> caller_ss       dw 0                    ;   if we use our own stack
   981                              <1> %endif
   982                              <1> 
   983                              <1>                 ; Pointers to commands
     0 00000168 [5B03]                  command_tbl     dw cmd_init             ;  0 Init
     0 0000016A [4E02]                                  dw cmd_media            ;  1 Media
     0 0000016C [7002]                                  dw cmd_BPB              ;  2 Build BPB
     0 0000016E [2602]                                  dw cmd_unknown          ;  3 IOCTL input
     0 00000170 [B402]                                  dw cmd_input            ;  4 Input
     0 00000172 [2602]                                  dw cmd_unknown          ;  5 nondest input (char)
     0 00000174 [2602]                                  dw cmd_unknown          ;  6 input status (char)
     0 00000176 [2602]                                  dw cmd_unknown          ;  7 input flush (char)
     0 00000178 [C502]                                  dw cmd_output           ;  8 Output
     0 0000017A [C502]                                  dw cmd_output           ;  9 Output with verify
     0 0000017C [2602]                                  dw cmd_unknown          ; 10 output status (char)
     0 0000017E [2602]                                  dw cmd_unknown          ; 11 output flush (char)
     0 00000180 [2602]                                  dw cmd_unknown          ; 12 IOCTL output
     0 00000182 [9202]                                  dw cmd_open             ; 13 Open device
     0 00000184 [9802]                                  dw cmd_close            ; 14 Close device
     0 00000186 [A502]                                  dw cmd_removable        ; 15 Removable media check
  1000                              <1> %if CAPABLE & C_GIOCTL
  1001                              <1>                 dw cmd_unknown          ; 16 Output untill busy (char)
  1002                              <1>                 dw cmd_unknown          ; 17
  1003                              <1>                 dw cmd_unknown          ; 18
  1004                              <1>                 dw cmd_GIOCTL           ; 19 Generic IOCTL
  1005                              <1>                 dw cmd_unknown          ; 20
  1006                              <1>                 dw cmd_unknown          ; 21
  1007                              <1>                 dw cmd_unknown          ; 22
  1008                              <1>                 dw cmd_getLogical       ; 23
  1009                              <1>                 dw cmd_setLogical       ; 24
  1010                              <1> %endif
  1011                              <1> 
     0 00000188 10                      high_cmd        db ($-offset command_tbl)/2  ; Number of supported commands
  1013                              <1> 
  1014                              <1> ;**************************************************************************
  1015                              <1> ;
  1016                              <1> ;                       Batch transfer of sectors
  1017                              <1> ;
  1018                              <1> ; This transfers sectors according to the parameters passed on stack
  1019                              <1> ; even if the sectors are on different drivers chained to this one.
  1020                              <1> ;
  1021                              <1> ; Returns how many sectors were NOT moved; ax = 0 means all OK.
  1022                              <1> ;
  1023                              <1> ; !!! This function destroys the contents of DS !!!
  1024                              <1> ;
  1025                              <1> ;**************************************************************************
  1026                              <1> 
  1027                              <1> batch_xfer      proc far
  1028                              <1>  %if 0
  1029                              <1>                 arg buffer:far ptr, sector:dword, count:word, RW:word
  1030                              <1>                 local byteoffset:dword, bytes:word
  1031                              <1>  %endif
  1032                              <1> 	lframe far
  1033                              <1> 	lpar word, ?RW
  1034                              <1> 	lpar word, ?count
  1035                              <1> 	lpar dword, ?sector
  1036                              <1> 	lpar dword, ?buffer
  1037                              <1> 	 %xdefine RW bp + ??RW
  1038                              <1> 	 %undef count
  1039                              <1> 	 %xdefine count bp + ??count
  1040                              <1> 	 %xdefine sector bp + ??sector
  1041                              <1> 	 %xdefine buffer bp + ??buffer
  1042                              <1> 	lvar dword, ?byteoffset
  1043                              <1> 	lvar word, ?bytes
  1044                              <1> 	 %xdefine byteoffset bp + ??byteoffset
  1045                              <1> 	 %undef bytes
  1046                              <1> 	 %xdefine bytes bp + ??bytes
     0 00000189 5589E583EC06            	lenter , sub
  1048                              <1> 
  1049                              <1>                 debug 'o',<word ptr buffer>
  1050                              <1>                 debug 's',<word ptr buffer+2>
  1051                              <1> 
  1052                              <1> %if CAPABLE & C_GIOCTL
  1053                              <1>                 test word [RW],-1                      ; Writing boot sector?
  1054                              <1>                 jz batch_notboot
  1055                              <1>                 mov ax,word ptr [sector]
  1056                              <1>                 or ax,word ptr [sector+2]
  1057                              <1>                 jnz batch_notboot
  1058                              <1> 
  1059                              <1>                 mov ds,word ptr [buffer+2]
  1060                              <1>                 assume ds:nothing
  1061                              <1>                 mov si,word ptr [buffer]
  1062                              <1>                 add si,bsBytesPerSec
  1063                              <1>                 mov ax,[si]
  1064                              <1>                 cmp ax,[cs:conf + c_BPB_bps]
  1065                              <1>                 jnz batch_notboot
  1066                              <1> 
  1067                              <1>                 push cs                         ; Copy new BPS to conf
  1068                              <1>                 pop es
  1069                              <1>                 mov di,offset conf + c_BPB_bps
  1070                              <1> 
  1071                              <1>                 mov cx,25
  1072                              <1>                 rep movsb
  1073                              <1> 
  1074                              <1>                 mov byte [cs:conf + c_media_change],0       ; Tell do not know if changed
  1075                              <1> batch_notboot:
  1076                              <1> %endif
     0 0000018F 0E                                      push cs
     0 00000190 1F                                      pop ds
  1079                              <1> 
     0 00000191 BE[2001]                                mov si,offset conf
  1081                              <1>                 ; DS:SI - conf of current driver (main here)
  1082                              <1>                 assume ds:nothing
  1083                              <1> 
  1084                              <1> batch_next_driver:
  1085                              <1>                 ; Transfer sector to byte offset to disk and count the
  1086                              <1>                 ; number of bytes to xfer.
     0 00000194 8B460A                                  mov ax,word ptr [sector]
     0 00000197 8B560C                                  mov dx,word ptr [sector+2]
     0 0000019A 8B4E0E                                  mov cx,[count]
  1090                              <1>                 debug 'a',ax
  1091                              <1>                 debug 'd',dx
  1092                              <1>                 debug 'c',cx
  1093                              <1> 
     0 0000019D 3B4416                                  cmp ax,[si + c_sectorsl]          ; Starting sector on disk?
     0 000001A0 1B5418                                  sbb dx,[si + c_sectorsh]
     0 000001A3 8B560C                                  mov dx,word ptr [sector+2]
     0 000001A6 733C                                    jae batch_to_next               ; No
  1098                              <1> 
     0 000001A8 01C8                                    add ax,cx                       ; Count ending sector
     0 000001AA 83D200                                  adc dx,0
  1101                              <1> 
     0 000001AD 3B5418                                  cmp dx,[si + c_sectorsh]          ; Ending sector on disk?
     0 000001B0 7207                                    jb batch_IO1                    ; Jump if is
     0 000001B2 2B4416                                  sub ax,[si + c_sectorsl]
     0 000001B5 7602                                    jbe batch_IO1                   ; Jump if is
  1106                              <1> 
     0 000001B7 29C1                                    sub cx,ax                       ; Count how many we CAN transfer
  1108                              <1>                 debug 'T',cx
  1109                              <1> batch_IO1:
     0 000001B9 51                                      push cx
     0 000001BA 89C8                                    mov ax,cx                       ; Count number of bytes to move
  1112                              <1>                 ;mul [si].c_BPB_bps
     0 000001BC 8A4C1A                                  mov cl,[si + c_bps_shift]
     0 000001BF D3E0                                    sal ax,cl
     0 000001C1 8946FA                                  mov word ptr [bytes],ax           ; Number of bytes to move
  1116                              <1> 
     0 000001C4 8B460C                                  mov ax,word ptr [sector+2]        ; Count starting byte
  1118                              <1>                 ;mul [si].c_BPB_bps
     0 000001C7 D3E0                                    sal ax,cl
     0 000001C9 89C1                                    mov cx,ax
     0 000001CB 8B460A                                  mov ax,word ptr [sector]
     0 000001CE F7641B                                  mul word [si + c_BPB_bps]
     0 000001D1 01CA                                    add dx,cx                       ; dx:ax is starting byte
     0 000001D3 8946FC                                  mov word ptr [byteoffset],ax
     0 000001D6 8956FE                                  mov word ptr [byteoffset+2],dx
  1126                              <1> 
     0 000001D9 FF5C02                                  call far [si + c_disk_IO]
     0 000001DC 58                                      pop ax                          ; Pop number of sectors
     0 000001DD 7209                                    jc batch_IOx                    ; I/O error
  1130                              <1> 
     0 000001DF 29460E                                  sub [count],ax                    ; All transferred?
     0 000001E2 7603                                    jbe batch_done                  ;  yes, so exit
  1133                              <1> 
  1134                              <1> %if CAPABLE & C_APPENDED
  1135                              <1>                 debug 'N',ax
  1136                              <1>                 push ax
  1137                              <1>                 ;mul [si].c_BPB_bps              ; Increment transfer offset
  1138                              <1>                 mov cl,[si + c_bps_shift]
  1139                              <1>                 sal ax,cl
  1140                              <1>                 add word ptr [buffer],ax          ;  which can not exceed 0FFFFh
  1141                              <1>                 pop ax
  1142                              <1> 
  1143                              <1>                 xor dx,dx
  1144                              <1>                 add ax,word ptr [sector]          ; Count new starting sector
  1145                              <1>                 adc dx,word ptr [sector+2]
  1146                              <1> batch_to_next:
  1147                              <1>                 sub ax,[si + c_sectorsl]          ; Subtract passed sectors
  1148                              <1>                 sbb dx,[si + c_sectorsh]
  1149                              <1>                 mov word ptr [sector],ax          ; And store the result
  1150                              <1>                 mov word ptr [sector+2],dx
  1151                              <1> 
  1152                              <1>                 mov si,[si + c_next]              ; Find next driver
  1153                              <1>                 or si,si
  1154                              <1>                 mov ds,si
  1155                              <1>                 mov si,[dr_conf]
  1156                              <1>                 jz batch_err
  1157                              <1>                 jmp batch_next_driver
  1158                              <1> 
  1159                              <1> %else    ;if CAPABLE and C_APPENDED
  1160                              <1> 
  1161                              <1> batch_to_next:
  1162                              <1> 
  1163                              <1> %endif   ;if CAPABLE and C_APPENDED
  1164                              <1> 
  1165                              <1> batch_err:
  1166                              <1>                 ; there is no next driver - sectors not found!
  1167                              <1>                 debug 'E',count
     0 000001E4 F9                                      stc
     0 000001E5 EB01                                    jmp batch_IOx
  1170                              <1> batch_done:
     0 000001E7 F8                                      clc
  1172                              <1> batch_IOx:
     0 000001E8 8B460E                                  mov ax,[count]
     0 000001EB 89EC5D                  	lleave
     0 000001EE CB                                      ret
  1176                              <1> 
  1177                              <1> 	 %undef RW
  1178                              <1> 	 %undef count
  1179                              <1> 	 %undef sector
  1180                              <1> 	 %undef buffer
  1181                              <1> 	 %undef bytesoffset
  1182                              <1> 	 %undef bytes
  1183                              <1> 
  1184                              <1>                 assume ds:d_seg
  1185                              <1> batch_xfer      endp
  1186                              <1> 
  1187                              <1>   
  1188                              <1> ;**************************************************************************
  1189                              <1> ;
  1190                              <1> ;                       Set request header address
  1191                              <1> ;
  1192                              <1> ; Called by DOS to set the request structure pointer
  1193                              <1> ;
  1194                              <1> ;**************************************************************************
  1195                              <1>   
  1196                              <1> strategy        proc far
     0 000001EF 2E891E[6401]                            mov word ptr [cs:req_ptr],bx
     0 000001F4 2E8C06[6601]                            mov word ptr [cs:req_ptr+2],es
     0 000001F9 CB                                      ret
  1200                              <1> strategy	endp
  1201                              <1>   
  1202                              <1>   
  1203                              <1> ;**************************************************************************
  1204                              <1> ;
  1205                              <1> ;                       Commands
  1206                              <1> ;
  1207                              <1> ; Called by DOS. Requested action defined in structure pointed by req_ptr.
  1208                              <1> ;
  1209                              <1> ;**************************************************************************
  1210                              <1>   
  1211                              <1> commands        proc far
  1212                              <1>                 assume ds:nothing
     0 000001FA 9C                                      pushf
     0 000001FB 50                                      push ax
     0 000001FC 53                                      push bx
     0 000001FD 51                                      push cx
     0 000001FE 52                                      push dx
     0 000001FF 56                                      push si
     0 00000200 57                                      push di
     0 00000201 1E                                      push ds
     0 00000202 06                                      push es
  1222                              <1> 
  1223                              <1>                 %if STACKSIZE
  1224                              <1>                 ; Switch into our own stack
  1225                              <1>                 mov [cs:caller_ss],ss
  1226                              <1>                 mov [cs:caller_sp],sp
  1227                              <1>                 push cs
  1228                              <1>                 pop ss
  1229                              <1>                 mov sp, offset end_of_resident
  1230                              <1> .patchstack: equ $ - 2
  1231                              <1>                 %endif
  1232                              <1> 
  1233                              <1> 		%if DEBUGGING
  1234                              <1>                 push bp
  1235                              <1>                 mov bp,sp
  1236                              <1>                 %endif
  1237                              <1> 
     0 00000203 FC                                      cld
     0 00000204 2EC536[6401]            		lds si,[cs:req_ptr]
  1240                              <1>                 assume ds:nothing
  1241                              <1> 		; We trust Microsoft that the unit is right at [si].rhUnit
     0 00000209 8B4C12                  		mov cx,[si + rwrBytesSec] 	; Sectors/Cmd line/BPB pointer
     0 0000020C 8B5414                  		mov dx,[si + rwrStartSec] 	; Start sector/Device number
     0 0000020F 8A5C02                  		mov bl,[si + rhFunction]
     0 00000212 30FF                                    xor bh,bh                       ; Count index to command_tbl
  1246                              <1>                 debug 'F',bx
     0 00000214 2E3A1E[8801]                            cmp bl,[cs:high_cmd]                 ; Is command supported?
     0 00000219 730B                                    jae cmd_unknown                 ; Jump if not
     0 0000021B D1E3                    		shl bx,1
     0 0000021D C47C0E                  		les di,[si + rwrBuffer]		; ES:DI = transfer address
     0 00000220 0E                      		push cs
     0 00000221 1F                      		pop ds				; DS to local data segment
  1253                              <1>                 assume ds:d_seg
     0 00000222 FFA7[6801]              		jmp [command_tbl + bx]		; Do command
  1255                              <1> cmd_unknown:
  1256                              <1>                 assume ds:nothing
     0 00000226 B80380                  		mov ax,ERROR | UNKNOWN_COMMAND
     0 00000229 EB11                    		jmp cmd_ret
  1259                              <1> cmd_IOerr:
     0 0000022B 2EC51E[6401]            		lds bx,[cs:req_ptr]
     0 00000230 C747120000              		mov word [bx + rwrBytesSec],0		; Sector count zero
  1262                              <1> cmd_error:
     0 00000235 B481                    		mov ah, (ERROR | DONE) >> 8	; ERROR and DONE (err #, in al)
     0 00000237 EB03                    		jmp cmd_ret
  1265                              <1> 
  1266                              <1> cmd_ok:
     0 00000239 B80001                  		mov ax,DONE
  1268                              <1> cmd_ret:
  1269                              <1>                 debug 'Q',ax
     0 0000023C 2EC51E[6401]            		lds bx,[cs:req_ptr]
     0 00000241 894703                  		mov [bx + rhStatus],ax
  1272                              <1> 
  1273                              <1>                 %if DEBUGGING
  1274                              <1>                 cmp bp,sp
  1275                              <1>                 je dbstack1
  1276                              <1>                 debug '/',sp
  1277                              <1>                 debug '/',bp
  1278                              <1> dbstack1:
  1279                              <1>                 mov sp,bp
  1280                              <1>                 pop bp
  1281                              <1>                 %endif
  1282                              <1> 
  1283                              <1>                 %if STACKSIZE
  1284                              <1>                 ; Switch back into callers stack
  1285                              <1>                 mov ss,[cs:caller_ss]
  1286                              <1>                 mov sp,[cs:caller_sp]
  1287                              <1> ;                cmp stack_check,STACK_CHECK_ID
  1288                              <1> ;                je cmd_stack_ok
  1289                              <1>                    ;report error
  1290                              <1> ;cmd_stack_ok:
  1291                              <1>                 %endif
  1292                              <1> 
     0 00000244 07                      		pop es
     0 00000245 1F                      		pop ds
     0 00000246 5F                      		pop di
     0 00000247 5E                      		pop si
     0 00000248 5A                      		pop dx
     0 00000249 59                      		pop cx
     0 0000024A 5B                      		pop bx
     0 0000024B 58                      		pop ax
     0 0000024C 9D                                      popf
     0 0000024D CB                      		retf				; Return far
  1303                              <1>                 assume ds:d_seg
  1304                              <1> commands	endp
  1305                              <1> 
  1306                              <1> ;**************************************************************************
  1307                              <1> ;
  1308                              <1> ;               Media Check command
  1309                              <1> ;
  1310                              <1> ;**************************************************************************
  1311                              <1> 
  1312                              <1> cmd_media       proc near
     0 0000024E C41E[6401]                              les bx,[req_ptr]
     0 00000252 A0[5901]                                mov al,[conf + c_media_change]      ; Read the change return
  1315                              <1>                 debug 'C',ax
  1316                              <1> 
     0 00000255 F606[5801]01                            test byte [conf + c_RW_access],READ_ACCESS
     0 0000025A 7410                                    jz dev_not_ready
  1319                              <1> 
     0 0000025C 2688470E                		mov [es:bx + mrReturn],al
     0 00000260 26C7470F[0B00]          		mov word ptr [es:bx + mrVolumeID],offset dr_volume
     0 00000266 268C4F11                		mov word ptr [es:bx + mrVolumeID + 2],cs
     0 0000026A EBCD                                    jmp cmd_ok
  1324                              <1> 
  1325                              <1> dev_not_ready:
     0 0000026C B002                                    mov al,DRIVE_NOT_READY
     0 0000026E EBC5                                    jmp cmd_error
  1328                              <1> 
  1329                              <1> cmd_media       endp
  1330                              <1> 
  1331                              <1> 
  1332                              <1> ;**************************************************************************
  1333                              <1> ;
  1334                              <1> ;               Build BPB command
  1335                              <1> ;
  1336                              <1> ;**************************************************************************
  1337                              <1> 
  1338                              <1> cmd_BPB         proc near
  1339                              <1>                 debug 'B',<conf.c_RW_access>
     0 00000270 F606[5801]01                            test byte [conf + c_RW_access],READ_ACCESS
     0 00000275 74F5                                    jz dev_not_ready
  1342                              <1> 
     0 00000277 C41E[6401]                              les bx,[req_ptr]
     0 0000027B 26C74712[3B01]                          mov word ptr [es:bx + bbrBPBAddress],offset BPB
     0 00000281 268C4F14                                mov word ptr [es:bx + bbrBPBAddress + 2],cs
     0 00000285 C706[5B01]0000                          mov word [conf + c_open_files],0         ; Reset open files to 0
     0 0000028B C606[5901]01                            mov byte [conf + c_media_change],1       ; Media no longer changed
     0 00000290 EBA7                                    jmp cmd_ok
  1349                              <1> cmd_BPB         endp
  1350                              <1> 
  1351                              <1> 
  1352                              <1> ;**************************************************************************
  1353                              <1> ;
  1354                              <1> ;               Device Open command
  1355                              <1> ;
  1356                              <1> ;**************************************************************************
  1357                              <1> 
  1358                              <1> cmd_open        proc near
  1359                              <1>                 debug 'O',-1
     0 00000292 FF06[5B01]                              inc word [conf + c_open_files]
     0 00000296 EBA1                                    jmp cmd_ok
  1362                              <1> cmd_open        endp
  1363                              <1> 
  1364                              <1> 
  1365                              <1> ;**************************************************************************
  1366                              <1> ;
  1367                              <1> ;               Device Close command
  1368                              <1> ;
  1369                              <1> ;**************************************************************************
  1370                              <1> 
  1371                              <1> cmd_close       proc near
     0 00000298 833E[5B01]00                            cmp word [conf + c_open_files],0
     0 0000029D 7404                                    jz cmd_close1
     0 0000029F FF0E[5B01]                              dec word [conf + c_open_files]
  1375                              <1> cmd_close1:
     0 000002A3 EB94                                    jmp cmd_ok
  1377                              <1> cmd_close       endp
  1378                              <1> 
  1379                              <1> 
  1380                              <1> ;**************************************************************************
  1381                              <1> ;
  1382                              <1> ;               Removable media query
  1383                              <1> ;
  1384                              <1> ;**************************************************************************
  1385                              <1> 
  1386                              <1> cmd_removable   proc near
     0 000002A5 B80001                                  mov ax,DONE
     0 000002A8 F606[5801]04                            test byte [conf + c_RW_access],4
     0 000002AD 7403                                    jz cmd_removable_x
     0 000002AF 0D0002                                  or ax,BUSY
  1391                              <1> cmd_removable_x:
     0 000002B2 EB88                                    jmp cmd_ret
  1393                              <1> cmd_removable   endp
  1394                              <1> 
  1395                              <1> ;**************************************************************************
  1396                              <1> ;
  1397                              <1> ;               INPUT command
  1398                              <1> ;
  1399                              <1> ;**************************************************************************
  1400                              <1> 
  1401                              <1> cmd_input       proc near
  1402                              <1>                 debug 'R',0
     0 000002B4 F606[5801]01                            test byte [conf + c_RW_access],READ_ACCESS
     0 000002B9 7405                                    jz cmd_input1
     0 000002BB 30DB                                    xor bl,bl
     0 000002BD 53                                      push bx                         ; Last parameter to batch_xfer
     0 000002BE EB13                                    jmp cmd_io
  1408                              <1> cmd_input1:
     0 000002C0 B002                                    mov al,DRIVE_NOT_READY
     0 000002C2 E966FF                                  jmp cmd_IOerr
  1411                              <1> cmd_input       endp
  1412                              <1> 
  1413                              <1> 
  1414                              <1> ;**************************************************************************
  1415                              <1> ;
  1416                              <1> ;               OUTPUT command
  1417                              <1> ;
  1418                              <1> ;**************************************************************************
  1419                              <1> 
  1420                              <1> cmd_output      proc near
  1421                              <1>                 debug 'W',0
     0 000002C5 B000                                    mov al,WRITE_PROTECT
     0 000002C7 B301                                    mov bl,1
     0 000002C9 F606[5801]02                            test byte [conf + c_RW_access],WRITE_ACCESS
     0 000002CE 7502                                    jnz to_cmd_io
     0 000002D0 EB54                                      jmp cmd_outerr
     0 000002D2 53                      to_cmd_io:      push bx                         ; Last parameter to batch_xfer
  1428                              <1> 
  1429                              <1> cmd_io:
  1430                              <1>                 ; CX    - sectors
  1431                              <1>                 ; ES:DI - transfer address
  1432                              <1>                 ; DS    = CS
  1433                              <1> 
     0 000002D3 89C8                                    mov ax,cx                       ; Count number of bytes to move
     0 000002D5 F726[3B01]                              mul word [conf + c_BPB_bps]
     0 000002D9 7204                                    jc cmd_output4                  ; Is it too much? (dx != 0)
  1437                              <1> 
  1438                              <1>                 ; check transfer address and count that they do not
  1439                              <1>                 ; exceed segment limit
     0 000002DB 01F8                                    add ax,di                       ; (dx = 0 after the mul)
     0 000002DD 730D                                    jnc cmd_output5
  1442                              <1> cmd_output4:
     0 000002DF 89F8                                    mov ax,di                       ; How many bytes CAN we move?
     0 000002E1 83F0FF                                  xor ax,-1
  1445                              <1>                 ;xor dx,dx                       ; How many sectors?
  1446                              <1>                 ;div conf.c_BPB_bps
     0 000002E4 8A0E[3A01]                              mov cl,[conf + c_bps_shift]
     0 000002E8 D3E8                                    shr ax,cl
     0 000002EA 89C1                                    mov cx,ax
  1450                              <1> cmd_output5:
     0 000002EC 51                                      push cx                         ; count parameter to batch_xfer
  1452                              <1>                                 
  1453                              <1> ;                mov cx,es
  1454                              <1> ;                les si,req_ptr
  1455                              <1> ;                mov [es:si].rwrBytesSec,dx     ; Xferred 0 sectors so far
  1456                              <1> ;                cmp [es:si].rwrLength,1Ah        ; Do we use 32-bit sec. address?
  1457                              <1> ;                jbe cmd_output3
  1458                              <1> ;                  debug '3',0
  1459                              <1> ;                  push word ptr [es:si].rwrHugeStartSec+2
  1460                              <1> ;                  push word ptr [es:si].rwrHugeStartSec
  1461                              <1> ;                  jmp cmd_output8
  1462                              <1> ;cmd_output3:
  1463                              <1> ;                xor dx,dx                       ; 16 bit sector parameter
  1464                              <1> ;                push dx                         ;  to batch_xfer
  1465                              <1> ;                push [es:si].rwrStartSec
  1466                              <1> 
     0 000002ED 8CC1                                    mov cx,es
     0 000002EF C436[6401]                              les si,[req_ptr]
     0 000002F3 268B4414                                mov ax,[es:si + rwrStartSec]
     0 000002F7 83F8FF                                  cmp ax,-1
     0 000002FA 750A                                    jne cmd_output3
  1472                              <1>                   debug '3',0
     0 000002FC 26FF741C                		  push word ptr [es:si + rwrHugeStartSec + 2]
     0 00000300 26FF741A                		  push word ptr [es:si + rwrHugeStartSec]
     0 00000304 EB04                                      jmp cmd_output8
  1476                              <1> cmd_output3:
     0 00000306 31D2                                    xor dx,dx                       ; 16 bit sector parameter
     0 00000308 52                                      push dx                         ;  to batch_xfer
     0 00000309 50                                      push ax
  1480                              <1> 
  1481                              <1> cmd_output8:
     0 0000030A 51                                      push cx                         ; buffer parameter to batch_xfer
     0 0000030B 57                                      push di
  1484                              <1> 
     0 0000030C 0E                      		push cs
     0 0000030D E879FE                                  call batch_xfer
  1487                              <1>                 assume ds:nothing
     0 00000310 720F                                    jc cmd_output1
     0 00000312 83C40C                                  add sp,12
  1490                              <1> 
     0 00000315 2EC436[6401]                            les si,[cs:req_ptr]
     0 0000031A 26294412                		sub [es:si + rwrBytesSec],ax     ;  actually transferred
  1493                              <1> cmd_output6:
     0 0000031E E918FF                                  jmp cmd_ok
  1495                              <1> 
  1496                              <1> cmd_output1:
     0 00000321 83C40C                                  add sp,12
  1498                              <1>                 debug 'S',ax
     0 00000324 B008                                    mov al,SECTOR_NOT_FOUND
  1500                              <1> cmd_outerr:
     0 00000326 E902FF                                  jmp cmd_IOerr
  1502                              <1>                 assume ds:d_seg
  1503                              <1> cmd_output      endp
  1504                              <1>   
  1505                              <1> 
  1506                              <1> %if 0
  1507                              <1> ;**************************************************************************
  1508                              <1> ;
  1509                              <1> ;               IOCTL write
  1510                              <1> ;
  1511                              <1> ; This function is used to switch to "inside DOS" and avoid some
  1512                              <1> ; multitaskin memory manager problems. We hope that the multitasker does
  1513                              <1> ; not free the memory if it is allocated here.
  1514                              <1> ;
  1515                              <1> ; The actual service routine is located in the caller at the address
  1516                              <1> ; where the data location is. Data size must be IOCTL_ID.
  1517                              <1> ;
  1518                              <1> ;**************************************************************************
  1519                              <1> 
  1520                              <1> cmd_IOCTL_write proc near
  1521                              <1>                 debug 'i',cx
  1522                              <1>                 cmp cx,IOCTL_ID         ; cx is the count
  1523                              <1>                 je cmd_iow1
  1524                              <1>                   jmp cmd_unknown
  1525                              <1> cmd_iow1:
  1526                              <1>                 lds si,[req_ptr]
  1527                              <1>                 assume ds:nothing
  1528                              <1>                 call [si + irwrBuffer]
  1529                              <1>                 jmp cmd_ok
  1530                              <1>                 assume ds:d_seg
  1531                              <1> cmd_IOCTL_write endp
  1532                              <1> %endif
  1533                              <1> 
  1534                              <1> 
  1535                              <1> ;**************************************************************************
  1536                              <1> ;
  1537                              <1> ;               GENERIC IOCTL
  1538                              <1> ;
  1539                              <1> ;**************************************************************************
  1540                              <1> 
     0 00000329 90<rep 7h>              	align 16, nop
  1542                              <1> %if CAPABLE & C_GIOCTL
  1543                              <1> %if STACKSIZE
  1544                              <1> noGIOCTL_eor equ offset $ + STACKSIZE   ; End of resident when no GIOCTL
  1545                              <1>                                         ; but when we have stack!
  1546                              <1> %else
  1547                              <1> noGIOCTL_eor equ offset $       ; End of resident when GIOCTL not supported
  1548                              <1> %endif
  1549                              <1> 
  1550                              <1> GIOCTL_MEDIA equ FALSE          ; If true, MID info is handled
  1551                              <1> 
  1552                              <1> %if GIOCTL_MEDIA
  1553                              <1> media_ID: ; NASM structure instance
  1554                              <1> MID_size equ MID_struc_size	; NASM port equate
  1555                              <1> istruc MID
  1556                              <1> at midInfoLevel
  1557                              <1> 	dw 0
  1558                              <1> at midSerialNum
  1559                              <1> 	dd 12345678h
  1560                              <1> at midVolLabel
  1561                              <1> 	times 11 db "SRDISK     "
  1562                              <1> at midFileSysType
  1563                              <1> 	times 8 db "FAT12   "
  1564                              <1> iend
  1565                              <1> %endif
  1566                              <1> 
  1567                              <1> gioctl_func_s struc
  1568                              <1> gioctl_fcode    db ?
  1569                              <1> gioctl_faddr    dw ?
  1570                              <1> gioctl_func_s ends
  1571                              <1> 
  1572                              <1> gioctl_func: ; NASM structure instance
  1573                              <1> gioctl_func_s_size equ gioctl_func_s_struc_size	; NASM port equate
  1574                              <1> istruc gioctl_func_s
  1575                              <1> at gioctl_fcode
  1576                              <1> 	db 41h
  1577                              <1> at gioctl_faddr
  1578                              <1> 	dw offset gioctl_write
  1579                              <1> iend
  1580                              <1> istruc gioctl_func_s
  1581                              <1> at gioctl_fcode
  1582                              <1> 	db 60h
  1583                              <1> at gioctl_faddr
  1584                              <1> 	dw offset gioctl_getparam
  1585                              <1> iend
  1586                              <1> istruc gioctl_func_s
  1587                              <1> at gioctl_fcode
  1588                              <1> 	db 61h
  1589                              <1> at gioctl_faddr
  1590                              <1> 	dw offset gioctl_read
  1591                              <1> iend
  1592                              <1> istruc gioctl_func_s
  1593                              <1> at gioctl_fcode
  1594                              <1> 	db 42h
  1595                              <1> at gioctl_faddr
  1596                              <1> 	dw offset cmd_ok
  1597                              <1> iend
  1598                              <1> istruc gioctl_func_s
  1599                              <1> at gioctl_fcode
  1600                              <1> 	db 62h
  1601                              <1> at gioctl_faddr
  1602                              <1> 	dw offset cmd_ok
  1603                              <1> iend
  1604                              <1> ;               gioctl_func_s <40h, offset gioctl_setparam>
  1605                              <1> %if GIOCTL_MEDIA
  1606                              <1> istruc gioctl_func_s
  1607                              <1> at gioctl_fcode
  1608                              <1> 	db 46h
  1609                              <1> at gioctl_faddr
  1610                              <1> 	dw offset gioctl_setmedia
  1611                              <1> iend
  1612                              <1> istruc gioctl_func_s
  1613                              <1> at gioctl_fcode
  1614                              <1> 	db 66h
  1615                              <1> at gioctl_faddr
  1616                              <1> 	dw offset gioctl_getmedia
  1617                              <1> iend
  1618                              <1> %endif
  1619                              <1> gioctl_func_end label byte
  1620                              <1> 
  1621                              <1> 
  1622                              <1> cmd_GIOCTL      proc near
  1623                              <1>                 les si,[req_ptr]
  1624                              <1> 		cmp byte [es:si + giCategory],8
  1625                              <1>                 jnz cmd_gioerr1
  1626                              <1> 
  1627                              <1> 		mov al,[es:si + giMinorCode]
  1628                              <1>                 debug 'G',ax
  1629                              <1> 
  1630                              <1> 		les si,[es:si + giIOCTLData]	; Parameter block
  1631                              <1>                 mov bx,offset gioctl_func
  1632                              <1> cmd_gionfunc:
  1633                              <1>                 cmp [bx + gioctl_fcode],al
  1634                              <1>                 je cmd_giodofunc
  1635                              <1>                 add bx,gioctl_func_s_struc_size
  1636                              <1>                 cmp bx,offset gioctl_func_end
  1637                              <1>                 jb cmd_gionfunc
  1638                              <1> cmd_gioerr1:
  1639                              <1>                 jmp cmd_unknown
  1640                              <1> cmd_giodofunc:
  1641                              <1>                 jmp [bx + gioctl_faddr]           ; Call with ES:SI -> param block
  1642                              <1> 
  1643                              <1> gioctl_dev_not_ready:
  1644                              <1>                 mov al,DRIVE_NOT_READY
  1645                              <1>                 jmp cmd_error
  1646                              <1> 
  1647                              <1> cmd_GIOCTL      endp
  1648                              <1> 
  1649                              <1> ;******** GIOCTL write (41h)
  1650                              <1> 
  1651                              <1> gioctl_write    proc near
  1652                              <1>                 test byte [conf + c_RW_access],WRITE_ACCESS
  1653                              <1>                 jz gioctl_write_prot
  1654                              <1> 
  1655                              <1>                 mov al,1
  1656                              <1>                 push ax                         ; RW parameter to batch_xfer
  1657                              <1>                 jmp track_xfer
  1658                              <1> 
  1659                              <1> gioctl_write_prot:
  1660                              <1>                 mov al,WRITE_PROTECT
  1661                              <1>                 jmp cmd_error
  1662                              <1> gioctl_write    endp
  1663                              <1> 
  1664                              <1> ;******** GIOCTL read (61h)
  1665                              <1> 
  1666                              <1> gioctl_read     proc near
  1667                              <1>                 test byte [conf + c_RW_access],READ_ACCESS
  1668                              <1>                 jz gioctl_dev_not_ready
  1669                              <1> 
  1670                              <1>                 mov al,0
  1671                              <1>                 push ax                         ; RW parameter to batch_xfer
  1672                              <1> track_xfer:
  1673                              <1>                 ; !!!! Expects c_BPB_heads * cylinders
  1674                              <1>                 ; and c_BPB_heads * c_BPB_spt less than 65536
  1675                              <1> 		push word [es:si + rwSectors]
  1676                              <1> 		mov ax,[es:si + rwCylinder]
  1677                              <1>                 mul word [conf + c_BPB_heads]
  1678                              <1>                 mul word [conf + c_BPB_spt]
  1679                              <1>                 mov bx,ax
  1680                              <1>                 mov cx,dx
  1681                              <1> 		mov ax,[es:si + rwHead]
  1682                              <1>                 mul word [conf + c_BPB_spt]
  1683                              <1> 		add ax,[es:si + rwFirstSector]
  1684                              <1>                 add ax,bx
  1685                              <1>                 adc dx,cx
  1686                              <1>                 push dx                         ; absolute sector
  1687                              <1>                 push ax
  1688                              <1> 
  1689                              <1> 		push word ptr [es:si + rwBuffer + 2] ; transfer address
  1690                              <1> 		push word ptr [es:si + rwBuffer]
  1691                              <1> 
  1692                              <1> 		push cs
  1693                              <1>                 call batch_xfer                 ; Destroys DS
  1694                              <1>                 add sp,12
  1695                              <1>                 jc track_xfer_IOerr
  1696                              <1> 
  1697                              <1>                 jmp cmd_ok
  1698                              <1> 
  1699                              <1> track_xfer_IOerr:
  1700                              <1>                 mov al,SECTOR_NOT_FOUND
  1701                              <1>                 jmp cmd_error
  1702                              <1> gioctl_read     endp
  1703                              <1> 
  1704                              <1> ;******** GIOCTL set parameters (40h)
  1705                              <1> 
  1706                              <1> 
  1707                              <1> %if 0
  1708                              <1> gioctl_setparam proc near
  1709                              <1> ;               test conf.c_RW_access,READ_ACCESS       ; !!!! Is this needed?
  1710                              <1> ;               jz gioctl_dev_not_ready
  1711                              <1> 
  1712                              <1>                 debug '0',<word ptr [es:si]>
  1713                              <1>                 debug '2',<word ptr [es:si+2]>
  1714                              <1>                 debug '4',<word ptr [es:si+4]>
  1715                              <1>                 debug '6',<word ptr [es:si+6]>
  1716                              <1>                 debug 'R',<word ptr [es:si].dpRootDirEnts>
  1717                              <1>                 debug 'S',<word ptr [es:si].dpSectors>  ; Sectors
  1718                              <1> 		debug 'M',<word ptr [es:si].dpMedia>    ; Media
  1719                              <1> ;               test byte ptr [es:si].dpSpecFunc,3 ; Change format?
  1720                              <1> ;               jnz gioctl_bad_media
  1721                              <1> ;               jmp cmd_ok
  1722                              <1> gioctl_bad_media:
  1723                              <1>                 mov al,UNKNOWN_MEDIA
  1724                              <1>                 jmp cmd_error
  1725                              <1> gioctl_setparam endp
  1726                              <1> %endif
  1727                              <1> 
  1728                              <1> ;******** GIOCTL get parameters (60h)
  1729                              <1> 
  1730                              <1> gioctl_getparam proc near
  1731                              <1> ;               test conf.c_RW_access,READ_ACCESS       ; !!!! Is this needed?
  1732                              <1> ;               jz gioctl_dev_not_ready
  1733                              <1> 
  1734                              <1>                 push ds
  1735                              <1>                 push es
  1736                              <1>                 pop ds
  1737                              <1>                 assume ds:nothing
  1738                              <1> 
  1739                              <1>                 ; Tell that we return info about current medium
  1740                              <1> ;               mov [si].dpSpecFunc,GETDPSF_CURRENT
  1741                              <1> 
  1742                              <1>                 mov al,[cs:conf + c_device_type]
  1743                              <1>                 mov [si + dpDevType],al
  1744                              <1>                 mov word [si + dpDevAttr],0   ; bit 0 Removable, bit 1 no change line
  1745                              <1> 
  1746                              <1>                 mov ax,[cs:conf + c_BPB_heads]
  1747                              <1>                 mul word [cs:conf + c_BPB_spt]              ; Implicit dx = 0
  1748                              <1>                 mov cx,ax
  1749                              <1>                 mov ax,[cs:conf + c_BPB_sectors]
  1750                              <1>                 or ax,ax
  1751                              <1>                 jnz gioctl_gp16bit
  1752                              <1>                   mov ax,[cs:conf + c_BPB_tsectorsl]   ; 32-bit disk
  1753                              <1>                   mov dx,[cs:conf + c_BPB_tsectorsh]
  1754                              <1> gioctl_gp16bit:
  1755                              <1>                 div cx
  1756                              <1>                 mov [si + dpCylinders],ax
  1757                              <1> 
  1758                              <1>                 mov byte [si + dpMediaType],0  ; Normal media
  1759                              <1> 
  1760                              <1>                 pop ds
  1761                              <1>                 assume ds:d_seg
  1762                              <1> 
  1763                              <1>                 mov di,si
  1764                              <1>                 mov si,offset conf + c_BPB_bps    ; ds:si -> current BPB
  1765                              <1>                 add di,7                        ; es:di -> Device Params BPB
  1766                              <1>                 mov cx,25
  1767                              <1>                 rep movsb               ; Copy BPB
  1768                              <1> 
  1769                              <1>                 jmp cmd_ok
  1770                              <1> gioctl_getparam endp
  1771                              <1> 
  1772                              <1> %if GIOCTL_MEDIA
  1773                              <1> gioctl_setmedia proc near
  1774                              <1>                 push es
  1775                              <1>                 pop ds
  1776                              <1>                 push cs
  1777                              <1>                 pop es
  1778                              <1>                 mov di,offset media_ID
  1779                              <1>                 mov cx,MID_struc_size
  1780                              <1>                 rep movsb
  1781                              <1>                 jmp cmd_ok
  1782                              <1> gioctl_setmedia endp
  1783                              <1> 
  1784                              <1> gioctl_getmedia proc near
  1785                              <1>                 mov di,si
  1786                              <1>                 mov si,offset media_ID
  1787                              <1>                 mov cx,MID_struc_size
  1788                              <1>                 rep movsb
  1789                              <1>                 jmp cmd_ok
  1790                              <1> gioctl_getmedia endp
  1791                              <1> %endif
  1792                              <1> 
  1793                              <1> cmd_getLogical  proc near
  1794                              <1>                 lds si,[req_ptr]
  1795                              <1>                 assume ds:nothing
  1796                              <1>                 debug 'l',<word ptr [si].ldrUnit>
  1797                              <1>                 mov byte [si + ldrUnit],0
  1798                              <1> to_cmd_ok:
  1799                              <1>                 jmp cmd_ok
  1800                              <1>                 assume ds:d_seg
  1801                              <1> cmd_getLogical  endp
  1802                              <1> 
  1803                              <1> cmd_setLogical  proc near
  1804                              <1>                 lds si,[req_ptr]
  1805                              <1>                 assume ds:nothing
  1806                              <1>                 debug 'L',<word ptr [si].ldrUnit>
  1807                              <1>                 cmp byte [si + ldrUnit],0
  1808                              <1>                 je to_cmd_ok
  1809                              <1>                 mov al,UNKNOWN_UNIT
  1810                              <1>                 jmp cmd_error
  1811                              <1>                 assume ds:d_seg
  1812                              <1> cmd_setLogical  endp
  1813                              <1> 
  1814                              <1> %endif ;if CAPABLE and C_GIOCTL
  1815                              <1> 
  1816                              <1> ;**************************************************************************
  1817                              <1> ;
  1818                              <1> ;               LOCAL STACK
  1819                              <1> ;
  1820                              <1> ; The stack replaces part of the initialization code.
  1821                              <1> ;**************************************************************************
  1822                              <1> 
  1823                              <1> %if STACKSIZE
  1824                              <1> ;stack_check     dw STACK_CHECK_ID
  1825                              <1> db STACKSIZE / 8 dup ('STACK   ')       ; To avoid stack over init code
  1826                              <1> align 16                                ; Make use of space left on page
  1827                              <1> %endif
  1828                              <1> 
  1829                              <1> end_of_resident EQU offset $
  1830                              <1> ; MARKS THE END OF RESIDENT PORTION OF DRIVER
  1831                              <1> 
  1832                              <1> ;**************************************************************************
  1833                              <1> ;**************************************************************************
  1834                              <1> ;**************************************************************************
  1835                              <1> ;**************************************************************************
  1836                              <1> ;
  1837                              <1> ;               INITIALIZATION TIME CODE
  1838                              <1> ;
  1839                              <1> ; This code and data is removed from the memory after driver is
  1840                              <1> ; initialized.
  1841                              <1> ;**************************************************************************
  1842                              <1> 
     0 00000330 00                      dos_drive       db 0                    ; DOS reported drive
     0 00000331 43                      def_drive       db 'C'                  ; Defined drive, where to install
  1845                              <1> 
     0 00000332 00                      install_ok      db FALSE                ; Installed OK
     0 00000333 00                      tryamisnumber:	db 0
  1848                              <1> 
     0 00000334 00000000                main_config     dd      0               ; Pointer to main configuration table
  1850                              <1> 
  1851                              <1> FLAG_1ST        EQU 1                   ; First SRDISK driver
  1852                              <1> FLAG_FORCEDRIVE EQU 2                   ; Force drive letter (in def_drive)
  1853                              <1> FLAG_APPEND     EQU 4                   ; Append to other SRDISK driver
  1854                              <1> FLAG_APPENDED   EQU 8                   ; Appended to other SRDISK driver
  1855                              <1> FLAG_KNOWDRIVE  EQU 10h                 ; Drive letter known
  1856                              <1> FLAG_32BITS     EQU 20h                 ; Capable of 32 bit sector addressing
  1857                              <1> FLAG_GIOCTL     EQU 40h                 ; Supports GIOCTL
     0 00000338 00                      flags           db 0
  1859                              <1> 
  1860                              <1> ;**************************************************************************
  1861                              <1> ;
  1862                              <1> ;                       prints macro
  1863                              <1> ;
  1864                              <1> ; This macro is used by initialization routines to display text.
  1865                              <1> ; dx must point to the '$' terminated text about to be displayed.
  1866                              <1> ;**************************************************************************
  1867                              <1>   
  1868                              <1> %macro prints 0
  1869                              <1> 		mov	ah,9
  1870                              <1>                 int     21h
  1871                              <1> %endmacro
  1872                              <1>   
  1873                              <1> %if DEBUGINIT
  1874                              <1> 
  1875                              <1> print_x         proc near               ; Print a dword in hex
  1876                              <1> print_lx:       push ax
  1877                              <1>                 mov ax,dx
  1878                              <1>                 call print_sx
  1879                              <1>                 mov ah,2
  1880                              <1>                 mov dl,':'
  1881                              <1>                 int 21h
  1882                              <1>                 pop ax
  1883                              <1> print_sx:                               ; Print a word in hex
  1884                              <1>                 push ax
  1885                              <1>                 mov al,ah
  1886                              <1>                 call print_cx
  1887                              <1>                 pop ax
  1888                              <1> %endif
  1889                              <1> print_cx:                               ; Print a byte in hex
     0 00000339 50                                      push ax
     0 0000033A D0E8                                    shr al,1
     0 0000033C D0E8                                    shr al,1
     0 0000033E D0E8                                    shr al,1
     0 00000340 D0E8                                    shr al,1
     0 00000342 E80100                                  call print_x1
     0 00000345 58                                      pop ax
     0 00000346 240F                    print_x1:       and al,0Fh              ; Print a hex digit
     0 00000348 3C0A                                    cmp al,10
     0 0000034A 7304                                    jae print_x2
     0 0000034C 0430                                      add al,'0'
     0 0000034E EB02                                      jmp print_x3
     0 00000350 0437                    print_x2:       add al,'A'-10
     0 00000352 B402                    print_x3:       mov ah,2
     0 00000354 52                                      push dx
     0 00000355 88C2                                    mov dl,al
     0 00000357 CD21                                    int 21h
     0 00000359 5A                                      pop dx
     0 0000035A C3                                      ret
  1909                              <1> print_x         endp
  1910                              <1> 
  1911                              <1> %if DEBUGINIT
  1912                              <1> idebugc  macro chr
  1913                              <1>         push ax
  1914                              <1>         mov al,[chr]
  1915                              <1>         call print_cx
  1916                              <1>         pop ax
  1917                              <1> endm
  1918                              <1> 
  1919                              <1> idebugs  macro wrd
  1920                              <1>         push ax
  1921                              <1>         mov ax,[wrd]
  1922                              <1>         call print_sx
  1923                              <1>         pop ax
  1924                              <1> endm
  1925                              <1> 
  1926                              <1> idebugl  macro high,low
  1927                              <1>         push ax
  1928                              <1>         push dx
  1929                              <1>         mov ax,[low]
  1930                              <1>         mov dx,[high]
  1931                              <1>         call print_lx
  1932                              <1>         mov ah,2
  1933                              <1>         mov dl,' '
  1934                              <1>         int 21h
  1935                              <1>         pop ax
  1936                              <1>         pop dx
  1937                              <1> endm
  1938                              <1> 
  1939                              <1> %else
  1940                              <1> 
  1941                              <1> %macro idebugc 1
  1942                              <1> %endmacro
  1943                              <1> 
  1944                              <1> %macro idebugs 1
  1945                              <1> %endmacro
  1946                              <1> 
  1947                              <1> %macro idebugl 2
  1948                              <1> %endmacro
  1949                              <1> 
  1950                              <1> %endif ; DEBUGINIT
  1951                              <1> 
  1952                              <1>   
  1953                              <1> ;**************************************************************************
  1954                              <1> ;
  1955                              <1> ;                       INIT command
  1956                              <1> ;
  1957                              <1> ; Init command does the following:
  1958                              <1> ;  - displays sign-on message
  1959                              <1> ;  - checks DOS version. This driver is built in a way that requires
  1960                              <1> ;    at least dos version 2.00. I'm not sure whether even that is enough.
  1961                              <1> ;  - determine which drive we are by default
  1962                              <1> ;  - read command line
  1963                              <1> ;    - abort on syntax errors
  1964                              <1> ;  - initialize multiplex interrupt
  1965                              <1> ;  - do hooks to other SRDISK drivers (specified in command line)
  1966                              <1> ;  - hook INT 19 bootstrap interrupt
  1967                              <1> ;  - fills in the request header
  1968                              <1> ;**************************************************************************
  1969                              <1>   
  1970                              <1> cmd_init        proc near
  1971                              <1>                 ; Compulsory initializations
     0 0000035B 8C0E[2401]                              mov word ptr [conf + c_disk_IO_seg],cs
  1973                              <1> 
  1974                              <1>                 ; Sign on message
     0 0000035F BA[A60A]                                mov dx,offset s_sign_on         ; "ReSizeable RAMdisk ver..."
  1976                              <1>                 prints
     0 00000362 B409                     mov ah,9
     0 00000364 CD21                     int 21h
  1977                              <1> 
  1978                              <1>                 ; Find out the features about DOS and the drive letter
     0 00000366 E8E300                                  call init_dos
     0 00000369 7303                                    jnc cmd_init4
     0 0000036B E98500                                    jmp cmd_init_err
  1982                              <1> cmd_init4:
     0 0000036E C436[6401]                              les si,[req_ptr]
  1984                              <1> 
  1985                              <1>                 idebugl es,si
  1986                              <1>                 idebugs <word ptr [es:si]>
  1987                              <1>                 idebugs <word ptr [es:si+2]>
  1988                              <1>                 idebugs <word ptr [es:si+16h]>
  1989                              <1> 
     0 00000372 A0[3003]                                mov al,[dos_drive]                ; Default install to drive
     0 00000375 A2[3103]                                mov [def_drive],al                ; .. reported by DOS
  1992                              <1> 
  1993                              <1>                 ; If DOS has no support for 32 bit sector access, disable it
     0 00000378 F606[3803]20                            test byte [flags],FLAG_32BITS
     0 0000037D 7505                                    jnz cmd_init2
     0 0000037F 8026[2101]FB                              and byte [conf + c_flags],~ C_32BITSEC
  1997                              <1>                   ;and drhdr_attr,NOT DHATTR_32BIT
  1998                              <1> cmd_init2:
  1999                              <1>                 ; If DOS has no support for GIOCTL (diskcopy) disable it
     0 00000384 F606[3803]40                            test byte [flags],FLAG_GIOCTL
     0 00000389 7505                                    jnz cmd_init5
     0 0000038B 8326[0400]BF                              and word [drhdr_attr],~ DHATTR_GIOCTL
  2003                              <1> cmd_init5:
     0 00000390 E84201                                  call init_read_cmdline
     0 00000393 725E                                    jc cmd_init_err
  2006                              <1> 
     0 00000395 E82102                                  call init_memory
     0 00000398 7259                                    jc cmd_init_err
  2009                              <1> 
     0 0000039A E8D002                                  call init_mplex
     0 0000039D 7254                                    jc cmd_init_err
  2012                              <1> 
     0 0000039F E88D03                                  call init_hooks
     0 000003A2 724F                                    jc cmd_init_err
  2015                              <1> %if HOOKINT19
  2016                              <1>                 call set_int19
  2017                              <1> %endif
  2018                              <1> 
     0 000003A4 A0[3103]                                mov al,[def_drive]
     0 000003A7 A2[2001]                                mov [conf + c_drive],al
  2021                              <1> 
  2022                              <1>                 ; --------------- If appended
     0 000003AA F606[3803]08                            test byte [flags],FLAG_APPENDED
     0 000003AF 7457                                    jz cmd_init7
     0 000003B1 A2[2C0B]                                  mov [s_appdrive],al     ; Report append
     0 000003B4 BA[170B]                                  mov dx,offset s_appended
  2027                              <1>                   prints
     0 000003B7 B409                     mov ah,9
     0 000003B9 CD21                     int 21h
     0 000003BB A0[DC00]                                  mov al, [i2D.multiplexnumber]
     0 000003BE E878FF                                    call print_cx
     0 000003C1 BA[3D0B]                                  mov dx, s_end
  2031                              <1>                   prints
     0 000003C4 B409                     mov ah,9
     0 000003C6 CD21                     int 21h
  2032                              <1> 
     0 000003C8 BB[8500]                                  mov bx,offset ret_far ; Strategy and commands short
     0 000003CB 891E[0600]                                mov [drhdr_strategy],bx
     0 000003CF 891E[0800]                                mov [drhdr_commands],bx
     0 000003D3 C706[0400]0080                            mov word [drhdr_attr],DHATTR_CHARDEV
     0 000003D9 C606[0A00]24                              mov byte [drhdr_units],'$'   ; Name for this driver '$SRD'MEMORY
  2038                              <1> 
     0 000003DE C51E[6401]                                lds bx,[req_ptr]
  2040                              <1>                   assume ds:nothing
     0 000003E2 C6470D01                		  mov byte [bx + irUnits],1
     0 000003E6 C7470E[3D01]            		  mov word ptr [bx + irEndAddress],appended_eor
     0 000003EB 2EC606[3203]01                            mov byte [cs:install_ok],TRUE
     0 000003F1 EB4B                                      jmp cmd_init3
  2045                              <1>                 assume ds:d_seg
  2046                              <1> cmd_init_err:   ; --------------- Error
  2047                              <1>                 prints
     0 000003F3 B409                     mov ah,9
     0 000003F5 CD21                     int 21h
  2048                              <1> cmd_init_abort:
     0 000003F7 E8B703                                  call deinit                     ; Remove hooks
     0 000003FA 31C0                                    xor ax,ax
     0 000003FC C51E[6401]                              lds bx,[req_ptr]
  2052                              <1>                 assume ds:nothing
     0 00000400 88470D                  		mov [bx + irUnits],al		; Zero the number of drives
     0 00000403 89470E                                  mov word ptr [bx + irEndAddress],ax
     0 00000406 EB36                                    jmp cmd_init3
  2056                              <1>                 assume ds:d_seg
  2057                              <1> 
  2058                              <1> cmd_init7:      ; --------------- Normal install
     0 00000408 A0[3103]                                mov al,[def_drive]
     0 0000040B A2[060B]                                mov [s_drive],al
     0 0000040E 3C24                                    cmp al,'$'                      ; Is the drive number known?
     0 00000410 7506                                    jne cmd_init8
     0 00000412 C706[060B]2020                            mov word [s_drive],2020h    ; Don't tell drive
  2064                              <1> cmd_init8:
     0 00000418 BA[F30A]                                mov dx,offset s_installed       ; Report install
  2066                              <1>                 prints
     0 0000041B B409                     mov ah,9
     0 0000041D CD21                     int 21h
     0 0000041F A0[DC00]                                mov al, [i2D.multiplexnumber]
     0 00000422 E814FF                                  call print_cx
     0 00000425 BA[3D0B]                                mov dx, s_end
  2070                              <1>                 prints
     0 00000428 B409                     mov ah,9
     0 0000042A CD21                     int 21h
     0 0000042C C606[3203]01                            mov byte [install_ok],TRUE
  2072                              <1> 
     0 00000431 C51E[6401]                              lds bx,[req_ptr]
  2074                              <1>                 assume ds:nothing
     0 00000435 C6470D01                		mov byte [bx + irUnits],1		; Save number of drives
     0 00000439 C7470E[3003]                            mov word ptr [bx + irEndAddress],end_of_resident
  2077                              <1> %if CAPABLE & C_GIOCTL
  2078                              <1>                 test byte [cs:flags],FLAG_GIOCTL
  2079                              <1>                 jnz cmd_init3
  2080                              <1>                   mov word ptr [bx + irEndAddress],noGIOCTL_eor
  2081                              <1>                   mov word [cs:commands.patchstack], noGIOCTL_eor
  2082                              <1>                   mov byte [cs:high_cmd],16
  2083                              <1> %endif
  2084                              <1> cmd_init3:      ; --------------- Return (whether failed or not)
     0 0000043E 8C4F10                  		mov word ptr [bx + irEndAddress + 2],cs
  2086                              <1> 
     0 00000441 C74712[6201]            		mov word ptr [bx + irParamAddress],offset pBPB
     0 00000446 8C4F14                  		mov word ptr [bx + irParamAddress + 2],cs
  2089                              <1> 
  2090                              <1>                 ; --------------- After install operations
  2091                              <1> %if CAPABLE & C_DISK_IMAGE
  2092                              <1>                 cmp byte [cs:install_ok],TRUE
  2093                              <1>                 jne cmd_init6
  2094                              <1>                   call load_image
  2095                              <1> cmd_init6:
  2096                              <1> %endif
     0 00000449 E9EDFD                                  jmp cmd_ok
  2098                              <1> 
  2099                              <1>                 assume ds:d_seg
  2100                              <1> cmd_init        endp
  2101                              <1> 
  2102                              <1> ;**************************************************************************
  2103                              <1> ;
  2104                              <1> ;               CHECK DOS VERSION AND CAPABILITIES
  2105                              <1> ;
  2106                              <1> ;**************************************************************************
  2107                              <1> 
  2108                              <1> init_dos        proc near
     0 0000044C B024                                    mov al,'$'
     0 0000044E A2[3003]                                mov [dos_drive],al
  2111                              <1> 
     0 00000451 B85244                                  mov ax,4452h    ; DR-DOS?
     0 00000454 F9                                      stc
     0 00000455 CD21                                    int 21h
     0 00000457 7221                                    jc idos_notc
     0 00000459 39D0                                    cmp ax,dx
     0 0000045B 751D                                    jne idos_notc
     0 0000045D 80FC10                                  cmp ah,10h
     0 00000460 7518                                    jne idos_notc   ; Not installed
  2120                              <1> 
     0 00000462 3C67                                    cmp al,67h      ; DR-DOS version 6.0 ?
     0 00000464 7514                                    jne idos_notc   ; If not, treat it like MS-DOS
  2123                              <1> 
     0 00000466 800E[3803]70                              or byte [flags],FLAG_32BITS | FLAG_GIOCTL | FLAG_KNOWDRIVE
     0 0000046B C436[6401]                                les si,[req_ptr]
     0 0000046F 268A4416                                  mov al,[es:si + irDriveNumber]
     0 00000473 0441                                      add al,'A'
     0 00000475 A2[3003]                                  mov [dos_drive],al
     0 00000478 EB59                                      jmp idos_x
  2130                              <1> 
     0 0000047A B430                    idos_notc:      mov ah,30h
     0 0000047C CD21                                    int 21h         ; Get DOS version number
  2133                              <1> 
     0 0000047E 86E0                                    xchg ah,al
  2135                              <1>                 idebugs ax
     0 00000480 3D0003                                  cmp ax,300h     ; Multiplex supported only after version 3.00
     0 00000483 730A                                    jnb idos2
  2138                              <1> ; Let's not be picky
  2139                              <1> ;                cmp ax,700h
  2140                              <1> ;                jb idos2
  2141                              <1> idos1:
     0 00000485 BA[9708]                                  mov dx,offset errs_eDOS       ; Invalid DOS version
     0 00000488 F9                                        stc
     0 00000489 C3                                        ret
  2145                              <1> 
     0 0000048A BA[B908]                i2Dinvalid:	mov dx, errs_i2D_invalid
     0 0000048D F9                      		stc
     0 0000048E C3                      		retn
  2149                              <1> 
  2150                              <1> idos2:
     0 0000048F 3D1403                                  cmp ax,314h	; DOS 3.20+ ?
     0 00000492 7205                                    jb idos3
     0 00000494 800E[3803]40                              or byte [flags],FLAG_GIOCTL
  2154                              <1> idos3:
     0 00000499 3D1F03                                  cmp ax,31Fh     ; DOS 3.31+ ?
     0 0000049C 7205                                    jb idos4
     0 0000049E 800E[3803]20                              or byte [flags],FLAG_32BITS
  2158                              <1> idos4:
  2159                              <1> 
     0 000004A3 31C0                    	xor ax, ax
     0 000004A5 8EC0                    	mov es, ax
     0 000004A7 26C436B400              	les si, [es:2Dh * 4]
     0 000004AC 83FEFF                  	cmp si, -1
     0 000004AF 74D9                    	je i2Dinvalid
     0 000004B1 8CC0                    	mov ax, es
     0 000004B3 85C0                    	test ax, ax
     0 000004B5 74D3                    	jz i2Dinvalid
  2168                              <1> 
     0 000004B7 C436[6401]                              les si,[req_ptr]
     0 000004BB 26803C16                                cmp byte ptr [es:si],16h        ; Device number supported?
     0 000004BF 7212                                    jb idos_x                       ; No, make a guess
     0 000004C1 C436[6401]                                les si,[req_ptr]
     0 000004C5 268A4416                                  mov al,[es:si + irDriveNumber]
     0 000004C9 0441                                      add al,'A'
     0 000004CB A2[3003]                                  mov [dos_drive],al
     0 000004CE 800E[3803]10                              or byte [flags],FLAG_KNOWDRIVE
  2177                              <1> idos_x:
  2178                              <1> 
  2179                              <1> ;; !!!! The following does not work since the drhdr_next is not valid yet.
  2180                              <1> ;
  2181                              <1> ;                cmp dos_drive,'C'               ; Is invalid drive?
  2182                              <1> ;                jb idosx1
  2183                              <1> ;                cmp dos_drive,'Z'
  2184                              <1> ;                jbe idosx2
  2185                              <1> ;idosx1:
  2186                              <1> ;                  les si,drhdr_next             ; Walk links up to count
  2187                              <1> ;                  mov al,'A'                    ; block devices
  2188                              <1> ;cntblk1:
  2189                              <1> ;                  cmp si,0FFFFh
  2190                              <1> ;                  je cntblk3
  2191                              <1> ;                    test [es:si].dhAttributes,DHATTR_CHARDEV
  2192                              <1> ;                    jnz cntblk2
  2193                              <1> ;                      add al,[es:si].dhNameOrUnits
  2194                              <1> ;cntblk2:
  2195                              <1> ;                    les si,[es:si].dhLink
  2196                              <1> ;                    jmp cntblk1
  2197                              <1> ;cntblk3:
  2198                              <1> ;                  mov dos_drive,al
  2199                              <1> ;                  or flags,FLAG_KNOWDRIVE
  2200                              <1> 
  2201                              <1> idosx2:
     0 000004D3 F8                                      clc
     0 000004D4 C3                                      ret
  2204                              <1> init_dos        endp
  2205                              <1> 
  2206                              <1>   
  2207                              <1> ;**************************************************************************
  2208                              <1> ;
  2209                              <1> ;               READ COMMAND LINE
  2210                              <1> ;
  2211                              <1> ; Return carry set if error
  2212                              <1> ;**************************************************************************
  2213                              <1> 
  2214                              <1> init_read_cmdline proc near
     0 000004D5 1E                                      push ds
  2216                              <1> 
     0 000004D6 C41E[6401]                              les bx,[req_ptr]
     0 000004DA 26C57712                		lds si,[es:bx + irParamAddress]	; Pointer to cmd line
  2219                              <1>                 assume ds:nothing
  2220                              <1> 
     0 000004DE AC                      irc1:           lodsb                           ; Skip over the driver name
     0 000004DF 3C09                                    cmp al,9 ;tab
     0 000004E1 7409                                    je irc2
     0 000004E3 3C20                                    cmp al,' '
     0 000004E5 7405                                    je irc2
     0 000004E7 77F5                                    ja irc1
     0 000004E9 E99F00                                  jmp irc_eol
  2228                              <1> irc2:
     0 000004EC E8C000                  irc_narg:       call irc_skip_space
  2230                              <1> 
     0 000004EF 3C20                                    cmp al,' '                      ; Every ctrl character ends
     0 000004F1 7303E99500                              jb irc_eol
  2233                              <1> 
     0 000004F6 3C2F                                    cmp al,'/'
     0 000004F8 7432                                    jz irc_switch
  2236                              <1> 
     0 000004FA 3C61                    		cmp al, 'a'
     0 000004FC 7206                    		jb @F
     0 000004FE 3C7A                    		cmp al, 'z'
     0 00000500 7702                    		ja @F
     0 00000502 24DF                                    and al,11011111b                ; Make lowercase to uppercase
  2242                              <1> @@:
     0 00000504 3C41                                    cmp al,'A'
     0 00000506 721E                                    jb irc_syntax
     0 00000508 3C60                                    cmp al,'`'
     0 0000050A 771A                                    ja irc_syntax
  2247                              <1> 
     0 0000050C 803C3A                                  cmp byte ptr [si],':'
     0 0000050F 7501                                    jne irc3
     0 00000511 46                                      inc si                          ; Skip ':'
  2251                              <1> irc3:           
     0 00000512 2EA2[3103]                              mov [cs:def_drive],al
     0 00000516 2EF606[3803]02                          test byte [cs:flags],FLAG_FORCEDRIVE
     0 0000051C 7508                                    jnz irc_syntax
     0 0000051E 2E800E[3803]02                          or byte [cs:flags],FLAG_FORCEDRIVE
     0 00000524 EBC6                                    jmp irc_narg
  2257                              <1> 
     0 00000526 BA[8609]                irc_syntax:     mov dx,offset errs_syntax
     0 00000529 F9                                      stc
     0 0000052A 1F                                      pop ds
     0 0000052B C3                                      ret
  2262                              <1> 
     0 0000052C AC                      irc_switch:     lodsb
     0 0000052D 24DF                                    and al,11011111b                ; Make lowercase to uppercase
     0 0000052F 3C41                                    cmp al,'A'
     0 00000531 744F                    		je .append
     0 00000533 3C4D                    		cmp al, 'M'
     0 00000535 75EF                    		jne irc_syntax
     0 00000537 AC                      		lodsb
     0 00000538 24DF                    		and al, ~20h
     0 0000053A 3C50                    		cmp al, 'P'
     0 0000053C 75E8                    		jne irc_syntax
     0 0000053E AC                      		lodsb
     0 0000053F 24DF                    		and al, ~20h
     0 00000541 3C58                    		cmp al, 'X'
     0 00000543 75E1                    		jne irc_syntax
  2277                              <1> .mpx:
     0 00000545 AC                      		lodsb
     0 00000546 3C09                    		cmp al, 9
     0 00000548 74FB                    		je .mpx
     0 0000054A 3C20                    		cmp al, 32
     0 0000054C 74F7                    		je .mpx
     0 0000054E 3C3D                    		cmp al, '='
     0 00000550 74F3                    		je .mpx
     0 00000552 3C3A                    		cmp al, ':'
     0 00000554 74EF                    		je .mpx
     0 00000556 E83500                  		call gethex
     0 00000559 72CB                    		jc irc_syntax
     0 0000055B 88C2                    		mov dl, al
  2290                              <1> .loopmpx:
     0 0000055D AC                      		lodsb
     0 0000055E E82D00                  		call gethex
     0 00000561 7216                    		jc .endmpx
     0 00000563 00D2                    		add dl, dl
     0 00000565 72BF                    		jc irc_syntax
     0 00000567 00D2                    		add dl, dl
     0 00000569 72BB                    		jc irc_syntax
     0 0000056B 00D2                    		add dl, dl
     0 0000056D 72B7                    		jc irc_syntax
     0 0000056F 00D2                    		add dl, dl
     0 00000571 72B3                    		jc irc_syntax
     0 00000573 00C2                    		add dl, al
     0 00000575 72AF                    		jc irc_syntax
     0 00000577 EBE4                    		jmp .loopmpx
  2305                              <1> 
  2306                              <1> .endmpx:
     0 00000579 2E8816[3303]            		mov byte [cs:tryamisnumber], dl
     0 0000057E 4E                      		dec si
     0 0000057F E96AFF                  		jmp irc_narg
  2310                              <1> 
  2311                              <1> .append:
     0 00000582 2E800E[3803]04                          or byte [cs:flags],FLAG_APPEND
     0 00000588 E961FF                                  jmp irc_narg
  2314                              <1> 
     0 0000058B F8                      irc_eol:        clc
     0 0000058C 1F                                      pop ds
     0 0000058D C3                                      ret
  2318                              <1> init_read_cmdline endp
  2319                              <1> 
  2320                              <1> 
  2321                              <1> gethex:
     0 0000058E 3C61                    	cmp al, 'a'
     0 00000590 7206                    	jb @F
     0 00000592 3C7A                    	cmp al, 'z'
     0 00000594 7702                    	ja @F
     0 00000596 2C20                    	sub al, 20h
  2327                              <1> @@:
     0 00000598 3C30                    	cmp al, '0'
     0 0000059A 7211                    	jb .err
     0 0000059C 3C39                    	cmp al, '9'
     0 0000059E 760A                    	jbe .decit
     0 000005A0 3C41                    	cmp al, 'A'
     0 000005A2 7209                    	jb .err
     0 000005A4 3C46                    	cmp al, 'F'
     0 000005A6 7705                    	ja .err
  2336                              <1> .hexit:
     0 000005A8 2C07                    	sub al, 'A' - ('9' + 1)
  2338                              <1> .decit:
     0 000005AA 2C30                    	sub al, '0'		; NC
     0 000005AC C3                      	retn
  2341                              <1> 
  2342                              <1> .err:
     0 000005AD F9                      	stc
     0 000005AE C3                      	retn
  2345                              <1> 
  2346                              <1> 
  2347                              <1> irc_skip_space  proc near
     0 000005AF AC                      ircs1:          lodsb
     0 000005B0 3C20                                    cmp al,' '
     0 000005B2 74FB                                    je ircs1
     0 000005B4 3C09                                    cmp al,9 ;tab
     0 000005B6 74F7                                    je ircs1
     0 000005B8 C3                                      ret
  2354                              <1> irc_skip_space  endp
  2355                              <1> 
  2356                              <1>                 assume ds:d_seg
  2357                              <1> 
  2358                              <1>   
  2359                              <1> ;**************************************************************************
  2360                              <1> ;
  2361                              <1> ;                       Memory initialization
  2362                              <1> ;
  2363                              <1> ; Returns
  2364                              <1> ;   carry set if error
  2365                              <1> ;**************************************************************************
  2366                              <1>   
  2367                              <1> init_memory     proc near
  2368                              <1> 
  2369                              <1> %if METHOD EQ 1
  2370                              <1> ; Get XMS driver API address
  2371                              <1> 
  2372                              <1>                 push es
  2373                              <1>                 mov ax,4300h
  2374                              <1>                 int 2Fh                         ; Get XMS installed status
  2375                              <1>                 cmp al,80h
  2376                              <1>                 jne @@init1                       ; Jump if not installed
  2377                              <1>                 mov ax,4310h
  2378                              <1>                 int 2Fh                         ; Get XMS entry point
  2379                              <1>                 jnc @@init2                       ; Jump if no error
  2380                              <1> @@init1:
  2381                              <1>                   mov dx,offset errs_noXMS      ; "No extended mem driver"
  2382                              <1>                   jmp @@init4
  2383                              <1> @@init2:
  2384                              <1>                 mov word ptr [XMS_alloc + XMS_entry],bx
  2385                              <1>                 mov word ptr [XMS_alloc + XMS_entry+2],es
  2386                              <1> 
  2387                              <1>                 mov ah,0                        ; Verify XMS version
  2388                              <1>                 call far [XMS_alloc + XMS_entry]
  2389                              <1>                 cmp ax,200h
  2390                              <1>                 jae @@init3
  2391                              <1>                   mov dx,offset errs_badXMS
  2392                              <1>                   jmp @@init4
  2393                              <1> @@init3:
  2394                              <1>                 mov     word [XMS_alloc + XMS_handle],0  ; Zero handle for no handle
  2395                              <1> 
  2396                              <1>                 clc
  2397                              <1>                 jmp     @@init_ret
  2398                              <1> @@init4:
  2399                              <1>                 stc
  2400                              <1> @@init_ret:
  2401                              <1>                 pop     es
  2402                              <1> %endif
  2403                              <1> 
  2404                              <1> %if METHOD EQ 2
     0 000005B9 06                                      push    es
  2406                              <1> 
     0 000005BA B86735                                  mov ax,3567h                    ; Compare device name
     0 000005BD CD21                                    int 21h
     0 000005BF BF0A00                                  mov di,0Ah
     0 000005C2 BE[DF07]                                mov si,offset EMM_name
     0 000005C5 B90800                                  mov cx,8
     0 000005C8 FC                                      cld
     0 000005C9 F3A6                                    repz cmpsb
     0 000005CB 7514                                    jne @@init1
  2415                              <1> 
     0 000005CD B440                                    mov ah,EMS_GET_STATUS           ; Get status of EMM
     0 000005CF CD67                                    int 67h
     0 000005D1 08E4                                    or ah,ah
     0 000005D3 750C                                    jnz @@init1
  2420                              <1> 
     0 000005D5 B441                                    mov ah,EMS_FRAME_SEGMENT        ; Get page frame address
     0 000005D7 CD67                                    int 67h
     0 000005D9 891E[8800]                              mov [EMS_alloc + EMS_frame],bx
     0 000005DD 08E4                                    or ah,ah
     0 000005DF 7406                                    jz @@init2
  2426                              <1> @@init1:
     0 000005E1 BA[E707]                                  mov dx,offset errs_noEMS      ; "No expanded mem driver"
     0 000005E4 E98300                                    jmp @@init4
  2429                              <1> @@init2:
     0 000005E7 B446                                    mov ah,EMS_GET_VERSION          ; Verify EMS version
     0 000005E9 CD67                                    int 67h
     0 000005EB 08E4                                    or ah,ah
     0 000005ED 75F2                                    jnz @@init1
     0 000005EF 3C40                                    cmp al,40h
     0 000005F1 7305                                    jae @@init3
     0 000005F3 BA[1708]                                  mov dx,offset errs_badEMS
     0 000005F6 EB72                                      jmp @@init4
  2438                              <1> @@init3:
  2439                              <1>                 ; Try out the functions that are needed
     0 000005F8 B443                                    mov ah,EMS_ALLOCATE
     0 000005FA BB0100                                  mov bx,1
     0 000005FD CD67                                    int 67h
     0 000005FF 08E4                                    or ah,ah
     0 00000601 7559                                    jnz @@init6
     0 00000603 8916[8600]                              mov [EMS_alloc + EMS_handle],dx
  2446                              <1> 
     0 00000607 B451                                    mov ah,EMS_REALLOCATE_PAGES
     0 00000609 BB0200                                  mov bx,2
     0 0000060C CD67                                    int 67h
     0 0000060E 08E4                                    or ah,ah
     0 00000610 7542                                    jnz @@init5
  2452                              <1> 
     0 00000612 B457                                    mov ah,EMS_MOVE_MEM_REGION
     0 00000614 B000                                    mov al,0
     0 00000616 BE[8A00]                                mov si,offset EMS_alloc + EMS_cblk
     0 00000619 C7040004                                mov word [si + EMS_sizel],400h
     0 0000061D C744020000                              mov word [si + EMS_sizeh],0
     0 00000622 C6440401                                mov byte [si + EMS_stype],1            ; Source in EMS
     0 00000626 895405                                  mov [si + EMS_shandle],dx
     0 00000629 C744070000                              mov word [si + EMS_soff],0
     0 0000062E C744090000                              mov word [si + EMS_spage],0
     0 00000633 C6440B01                                mov byte [si + EMS_dtype],1            ; Destination in EMS
     0 00000637 89540C                                  mov [si + EMS_dhandle],dx
     0 0000063A C7440E0002                              mov word [si + EMS_doff],200h
     0 0000063F C744100100                              mov word [si + EMS_dpage],1
     0 00000644 CD67                                    int 67h
     0 00000646 08E4                                    or ah,ah
     0 00000648 750A                                    jnz @@init5
  2469                              <1> 
     0 0000064A B445                                    mov ah,EMS_DEALLOCATE
     0 0000064C 8B16[8600]                              mov dx,[EMS_alloc + EMS_handle]
     0 00000650 CD67                                    int 67h
     0 00000652 740D                                    jz @@init7
  2474                              <1> 
  2475                              <1> @@init5:
     0 00000654 B445                                    mov ah,EMS_DEALLOCATE
     0 00000656 8B16[8600]                              mov dx,[EMS_alloc + EMS_handle]
     0 0000065A CD67                                    int 67h
  2479                              <1> @@init6:
     0 0000065C BA[4708]                                mov dx,offset errs_nofuncEMS
     0 0000065F EB09                                    jmp @@init4
  2482                              <1> 
  2483                              <1> @@init7:
     0 00000661 C706[8600]FFFF                          mov word [EMS_alloc + EMS_handle],-1 ; -1 handle for no handle
  2485                              <1> 
     0 00000667 F8                                      clc
     0 00000668 EB01                                    jmp     @@init_ret
  2488                              <1> @@init4:
     0 0000066A F9                                      stc
  2490                              <1> @@init_ret:
     0 0000066B 07                                      pop     es
  2492                              <1> %endif
  2493                              <1> 
  2494                              <1> %if METHOD EQ 3
  2495                              <1>                 push    es
  2496                              <1> 
  2497                              <1>                 mov ax,3567h                    ; Compare device name
  2498                              <1>                 int 21h
  2499                              <1>                 mov di,0Ah
  2500                              <1>                 mov si,offset EMM_name
  2501                              <1>                 mov cx,8
  2502                              <1>                 cld
  2503                              <1>                 repz cmpsb
  2504                              <1>                 jne @@init1
  2505                              <1> 
  2506                              <1>                 mov ah,EMS_GET_STATUS           ; Get status of EMM
  2507                              <1>                 int 67h
  2508                              <1>                 or ah,ah
  2509                              <1>                 jnz @@init1
  2510                              <1> 
  2511                              <1>                 mov ah,EMS_FRAME_SEGMENT        ; Get page frame address
  2512                              <1>                 int 67h
  2513                              <1>                 mov [EMS_alloc + EMS_frame],bx
  2514                              <1>                 or ah,ah
  2515                              <1>                 jz @@init2
  2516                              <1> @@init1:
  2517                              <1>                   mov dx,offset errs_noEMS      ; "No expanded mem driver"
  2518                              <1>                   jmp @@init4
  2519                              <1> @@init2:
  2520                              <1>                 mov ah,EMS_GET_VERSION          ; Verify EMS version
  2521                              <1>                 int 67h
  2522                              <1>                 or ah,ah
  2523                              <1>                 jnz @@init1
  2524                              <1>                 cmp al,40h
  2525                              <1>                 jae @@init3
  2526                              <1>                   mov dx,offset errs_badEMS
  2527                              <1>                   jmp @@init4
  2528                              <1> @@init3:
  2529                              <1>                 ; Try out the functions that are needed
  2530                              <1>                 mov ah,EMS_ALLOCATE
  2531                              <1>                 mov bx,1
  2532                              <1>                 int 67h
  2533                              <1>                 or ah,ah
  2534                              <1>                 jnz @@init6
  2535                              <1>                 mov [EMS_alloc + EMS_handle],dx
  2536                              <1> 
  2537                              <1>                 mov ah,EMS_DEALLOCATE
  2538                              <1>                 mov dx,[EMS_alloc + EMS_handle]
  2539                              <1>                 int 67h
  2540                              <1>                 jz @@init7
  2541                              <1> 
  2542                              <1> @@init6:
  2543                              <1>                 mov dx,offset errs_nofuncEMS
  2544                              <1>                 jmp @@init4
  2545                              <1> 
  2546                              <1> @@init7:
  2547                              <1>                 mov word [EMS_alloc + EMS_handle],-1 ; -1 handle for no handle
  2548                              <1> 
  2549                              <1>                 clc
  2550                              <1>                 jmp     @@init_ret
  2551                              <1> @@init4:
  2552                              <1>                 stc
  2553                              <1> @@init_ret:
  2554                              <1>                 pop     es
  2555                              <1> %endif
  2556                              <1> 
     0 0000066C C3                                      ret
  2558                              <1> init_memory     endp
  2559                              <1> 
  2560                              <1> ;**************************************************************************
  2561                              <1> ;
  2562                              <1> ;               Multiplex service initialization
  2563                              <1> ;
  2564                              <1> ; Queries multiplex interrupt to find out if SRDISK device drivers are
  2565                              <1> ; already installed. If yes, hook our ctrl0 into the primary header.
  2566                              <1> ; if no, ctrl0 points to ourself. Always install our AMIS multiplexer.
  2567                              <1> ;
  2568                              <1> ; Return carry set if error.
  2569                              <1> ;**************************************************************************
  2570                              <1> 
  2571                              <1> init_mplex      proc near
     0 0000066D 31C0                    	xor ax, ax
  2573                              <1> .loop:
     0 0000066F B000                    	mov al, 0
     0 00000671 CD2D                    	int 2Dh			; installation check
     0 00000673 3CFF                    	cmp al, -1
     0 00000675 7419                    	je .check
  2578                              <1> .next:
     0 00000677 FEC4                    	inc ah
     0 00000679 75F4                    	jnz .loop
  2581                              <1> .new:
     0 0000067B C706[3403][2001]        	mov word [main_config], conf
     0 00000681 8C1E[3603]              	mov word [main_config + 2], ds
     0 00000685 800E[3803]01            	or byte [flags], FLAG_1ST
     0 0000068A 8C1E[9E00]              	mov word [ctrl0 + 2], ds; offset already set (0)
     0 0000068E EB5C                    	jmp .install
  2587                              <1> 
  2588                              <1> .check:
     0 00000690 8EC2                    	mov es, dx
     0 00000692 B90800                  	mov cx, words(16)
     0 00000695 BE[A000]                	mov si, amis_sign
     0 00000698 F3A7                    	repe cmpsw
     0 0000069A 75DB                    	jne .next
  2594                              <1> .found:
     0 0000069C B010                    	mov al, 10h
     0 0000069E CD2D                    	int 2Dh			; get compatible version
     0 000006A0 84C0                    	test al, al		; call supported ?
     0 000006A2 7503E98100              	jz .versionmismatch
     0 000006A7 81F90A02                	cmp cx, 200h + 10	; compatible to v2.10 ?
     0 000006AB 757B                    	jne .versionmismatch
     0 000006AD B020                    	mov al, 20h
     0 000006AF CD2D                    	int 2Dh			; get device driver header
     0 000006B1 3C04                    	cmp al, 4		; call supported ?
     0 000006B3 7573                    	jne .versionmismatch
  2605                              <1> 		; now dx:bx -> ctrl0
     0 000006B5 8EC2                    	mov es, dx		; => found ctrl0
     0 000006B7 26C41F                  	les bx, [es:bx]		; -> primary header
     0 000006BA 891E[9C00]              	mov word [ctrl0], bx
     0 000006BE 8C06[9E00]              	mov word [ctrl0 + 2], es; refer to primary header
     0 000006C2 85DB                    	test bx, bx
     0 000006C4 7562                    	jnz .versionmismatch
     0 000006C6 26813E[0B00]5352                        cmp word [es:dr_ID],'SR'	; Is it SRDISK structure?	; NASM port swapped text literals
     0 000006CD 7559                                    jne .versionmismatch		; No, multiplex used elsewhere
     0 000006CF 26803E[0D00]44                          cmp byte [es:dr_ID+2],'D'
     0 000006D5 7551                                    jne .versionmismatch		; No, multiplex used elsewhere
     0 000006D7 26803E[1700]01                          cmp byte [es:dr_v_format],V_FORMAT ; Proper version?
     0 000006DD 7549                                    jne .versionmismatch		; No, multiplex used elsewhere
  2618                              <1>                 ; OK
     0 000006DF 268B3E[1800]                            mov di,[es:dr_conf]
     0 000006E4 893E[3403]                              mov word ptr [main_config],di
     0 000006E8 8C06[3603]                              mov word ptr [main_config+2],es
  2622                              <1> 
  2623                              <1> .install:
     0 000006EC 2E8A26[3303]            	mov ah, byte [cs:tryamisnumber]
     0 000006F1 B000                    	mov al, 0
     0 000006F3 CD2D                    	int 2Dh
     0 000006F5 3C00                    	cmp al, 0
     0 000006F7 7413                    	je .foundfree
     0 000006F9 31C0                    	xor ax, ax
  2630                              <1> .loopfree:
     0 000006FB B000                    	mov al, 0
     0 000006FD CD2D                    	int 2Dh
     0 000006FF 3C00                    	cmp al, 0
     0 00000701 7409                    	je .foundfree
     0 00000703 FEC4                    	inc ah
     0 00000705 75F4                    	jnz .loopfree
     0 00000707 BA[E508]                	mov dx, errs_i2D_no_free
     0 0000070A EB1F                    	jmp .error
  2639                              <1> 
  2640                              <1> .foundfree:
     0 0000070C 8826[DC00]              	mov byte [i2D.multiplexnumber], ah
     0 00000710 B82D35                  	mov ax, 352Dh
     0 00000713 CD21                    	int 21h
     0 00000715 8C06[CC00]              	mov word [i2D.next + 2], es
     0 00000719 891E[CA00]              	mov word [i2D.next], bx
     0 0000071D BA[C800]                	mov dx, i2D
     0 00000720 B82D25                  	mov ax, 252Dh
     0 00000723 CD21                    	int 21h
  2649                              <1> 
     0 00000725 F8                      	clc
     0 00000726 EB04                    	jmp @F
  2652                              <1> 
  2653                              <1> .versionmismatch:
     0 00000728 BA[1209]                                mov dx,offset errs_ml_version
  2655                              <1> .error:
     0 0000072B F9                      		stc
  2657                              <1> @@:
     0 0000072C 1E                      		push ds
     0 0000072D 07                      		pop es
     0 0000072E C3                      		retn
  2661                              <1> init_mplex      endp
  2662                              <1> 
  2663                              <1> 
  2664                              <1> ;**************************************************************************
  2665                              <1> ;
  2666                              <1> ;               INIT HOOKS to previous SRDISK drivers
  2667                              <1> ;
  2668                              <1> ; Append this driver into the list of installed SRDISK drivers
  2669                              <1> ; Return carry set if error
  2670                              <1> ;**************************************************************************
  2671                              <1> 
  2672                              <1> init_hooks      proc near
     0 0000072F F606[3803]01                            test byte [flags],FLAG_1ST     ; If we are the first driver
     0 00000734 7561                                    jnz ihxok               ;  no hooks are to be done
  2675                              <1> 
     0 00000736 C43E[3403]                              les di,[main_config]      ; es:di point to a drive config
     0 0000073A A0[3103]                                mov al,[def_drive]        ; al is the drive to search
     0 0000073D 3C24                                    cmp al,'$'              ; Is drive letter unknown?
     0 0000073F 740E                                    je ih_nodrive           ; Yes, do not check drive letter
  2680                              <1> 
     0 00000741 F606[3803]04                            test byte [flags],FLAG_APPEND          ; If we append
     0 00000746 7409                                    jz ih_find_drive
     0 00000748 F606[3803]02                            test byte [flags],FLAG_FORCEDRIVE      ; but not specify drive
     0 0000074D 7502                                    jnz ih_find_drive
     0 0000074F B0FF                    ih_nodrive:       mov al,-1                     ; make sure drive not found
  2686                              <1> ih_find_drive:
     0 00000751 263805                  ih1:            cmp [es:di + c_drive],al          ; Is it the same drive?
     0 00000754 741C                                    je ih_append
     0 00000756 26F7453DFFFF            ih2:            test word ptr [es:di + c_next_drive],-1 ; Is there next drive
     0 0000075C 7446                                    jz ih_newdrive                  ; No (valid segment is nonzero)
     0 0000075E 268E453D                                mov es,[es:di + c_next_drive]     ; Yes, find the next drive
     0 00000762 268B3E[1800]                            mov di,[es:dr_conf]
     0 00000767 EBE8                                    jmp ih1
  2694                              <1> 
  2695                              <1> ih_append_new:  ; Append this driver into previously installed drive
     0 00000769 268A05                                  mov al,[es:di + c_drive]          ; Find the drive letter
     0 0000076C A2[3103]                                mov [def_drive],al
     0 0000076F A2[2001]                                mov [conf + c_drive],al
  2699                              <1> 
  2700                              <1> ih_append:      ; Append this driver into specified drive
     0 00000772 26F6450101                              test byte [es:di + c_flags],C_APPENDED ; Append allowed?
     0 00000777 7413                                    jz ih_appendfail                ; No, fail
  2703                              <1> 
     0 00000779 26F7450AFFFF                            test word ptr [es:di + c_next],-1 ; Is there next driver
     0 0000077F 7418                                    jz ih_a1                        ; No, append here
     0 00000781 268E450A                                mov es,[es:di + c_next]           ; Yes, find the next drive
     0 00000785 268B3E[1800]                            mov di,[es:dr_conf]
     0 0000078A EBE6                                    jmp ih_append
  2709                              <1> 
     0 0000078C A0[3003]                ih_appendfail:  mov al,[dos_drive]
     0 0000078F A2[3103]                                mov [def_drive],al
     0 00000792 BA[4C09]                                mov dx,offset errs_noappend
     0 00000795 F9                                      stc
     0 00000796 C3                                      ret
  2715                              <1> 
     0 00000797 F8                      ihxok:          clc
     0 00000798 C3                      ihx:            ret
  2718                              <1> 
     0 00000799 268C5D0A                ih_a1:          mov [es:di + c_next],ds
     0 0000079D 800E[3803]08                            or byte [flags],FLAG_APPENDED  ; Remember to free extra memory
  2721                              <1> %if DEBUGGING
  2722                              <1>                 mov ax,[es:d_col]         ; Debug data display little left from
  2723                              <1>                 sub ax,16               ;  main data display
  2724                              <1>                 mov [d_col],ax
  2725                              <1> %endif ;DEBUGGING
     0 000007A2 EBF3                                    jmp ihxok
  2727                              <1> 
     0 000007A4 F606[3803]04            ih_newdrive:    test byte [flags],FLAG_APPEND
     0 000007A9 75BE                                    jnz ih_append_new
  2730                              <1>                 ; This driver must be placed at the tail of list of
  2731                              <1>                 ; SRDISK drivers
     0 000007AB 268C5D3D                                mov [es:di + c_next_drive],ds
  2733                              <1> 
     0 000007AF EBE6                                    jmp ihxok
  2735                              <1> init_hooks      endp
  2736                              <1> 
  2737                              <1> 
  2738                              <1> ;**************************************************************************
  2739                              <1> ;
  2740                              <1> ;                       INT 19 hooking
  2741                              <1> ;
  2742                              <1> ; INT 19 is the bootstrap loader interrupt, which is invoked when user
  2743                              <1> ; presses Ctrl-Alt-Del. We must hook it in order to release the
  2744                              <1> ; extended memory allocated for RAM disk.
  2745                              <1> ;**************************************************************************
  2746                              <1>   
  2747                              <1> %if HOOKINT19
  2748                              <1> 
  2749                              <1> set_int19       proc near
  2750                              <1> 		push ax
  2751                              <1> 		push dx
  2752                              <1> 		push bx
  2753                              <1> 		push es
  2754                              <1> 
  2755                              <1>                 mov ax,3519h
  2756                              <1>                 int 21h                         ; Get old int 19 handler
  2757                              <1>                 mov [old_int19 + 0],bx
  2758                              <1>                 mov [old_int19 + 2],es
  2759                              <1>                 mov dx,offset int_19_entry
  2760                              <1> 		mov ax,2519h
  2761                              <1>                 int 21h                         ; Set new int 19 handler
  2762                              <1> 
  2763                              <1> 		pop es
  2764                              <1> 		pop bx
  2765                              <1> 		pop dx
  2766                              <1> 		pop ax
  2767                              <1> 		retn
  2768                              <1> set_int19       endp
  2769                              <1>   
  2770                              <1> %endif
  2771                              <1> 
  2772                              <1> ;**************************************************************************
  2773                              <1> ;
  2774                              <1> ;               Deinitialization in case of aborted install
  2775                              <1> ;
  2776                              <1> ;**************************************************************************
  2777                              <1> 
  2778                              <1> deinit          proc near
  2779                              <1> %if HOOKINT19
  2780                              <1>                 mov ax,[old_int19 + 2]
  2781                              <1>                 or ax,[old_int19 + 0]
  2782                              <1>                 jz di_noint19
  2783                              <1> 
  2784                              <1>                 push ds
  2785                              <1>                 lds dx, [old_int19]
  2786                              <1>                 mov ax,2519h
  2787                              <1>                 int 21h                         ; Set old int 19 handler
  2788                              <1>                 pop ds
  2789                              <1> di_noint19:
  2790                              <1> %endif
  2791                              <1> 
  2792                              <1> ;**************************************************************************
  2793                              <1> ;
  2794                              <1> ;                       Memory deinitialization
  2795                              <1> ;
  2796                              <1> ;**************************************************************************
  2797                              <1> 
  2798                              <1> %if METHOD EQ 1
  2799                              <1>                 cmp word [XMS_alloc + XMS_handle],0
  2800                              <1>                 je @@done
  2801                              <1> 
  2802                              <1>                 mov dx,[XMS_alloc + XMS_handle]
  2803                              <1>                 mov ah,0Ah
  2804                              <1>                 call far [XMS_alloc + XMS_entry]        ; Free XMS memory
  2805                              <1>                 mov word [XMS_alloc + XMS_handle],0
  2806                              <1> @@done:
  2807                              <1> %endif
  2808                              <1> 
  2809                              <1> %if METHOD EQ 2
     0 000007B1 833E[8600]FF                            cmp word [EMS_alloc + EMS_handle],-1
     0 000007B6 740E                                    je @@done
  2812                              <1> 
     0 000007B8 8B16[8600]                              mov dx,[EMS_alloc + EMS_handle]
     0 000007BC B445                                    mov ah,EMS_DEALLOCATE
     0 000007BE CD67                                    int 67h                         ; Free EMS memory
     0 000007C0 C706[8600]FFFF                          mov word [EMS_alloc + EMS_handle],-1
  2817                              <1> @@done:
  2818                              <1> %endif
  2819                              <1> 
  2820                              <1> %if METHOD EQ 3
  2821                              <1>                 cmp word [EMS_alloc + EMS_handle],-1
  2822                              <1>                 je @@done
  2823                              <1> 
  2824                              <1>                 mov dx,[EMS_alloc + EMS_handle]
  2825                              <1>                 mov ah,EMS_DEALLOCATE
  2826                              <1>                 int 67h                         ; Free EMS memory
  2827                              <1>                 mov word [EMS_alloc + EMS_handle],-1
  2828                              <1> @@done:
  2829                              <1> %endif
  2830                              <1> 
  2831                              <1> old_multiplex equ i2D.next
     0 000007C6 A1[CA00]                                mov ax,word ptr [old_multiplex]
     0 000007C9 0B06[CC00]                              or ax,word ptr [old_multiplex+2]
     0 000007CD 740F                                    jz no_mplex
  2835                              <1> 
     0 000007CF 1E                                      push ds
     0 000007D0 8B16[CA00]                              mov dx,word ptr [old_multiplex]
     0 000007D4 8E1E[CC00]                              mov ds,word ptr [old_multiplex+2]
     0 000007D8 B82D25                                  mov ax,252Dh
     0 000007DB CD21                                    int 21h                         ; Set old multiplex handler
     0 000007DD 1F                                      pop ds
  2842                              <1> no_mplex:
  2843                              <1> 
     0 000007DE C3                                      ret
  2845                              <1> deinit          endp
  2846                              <1> 
  2847                              <1> 
  2848                              <1> ;**************************************************************************
  2849                              <1> ;
  2850                              <1> ;               Loading of included disk image
  2851                              <1> ;
  2852                              <1> ;**************************************************************************
  2853                              <1> 
  2854                              <1> %if CAPABLE & C_DISK_IMAGE
  2855                              <1> load_image      proc near
  2856                              <1>                 test byte [flags],FLAG_APPENDED
  2857                              <1>                 jz li1
  2858                              <1>                 ; If appended, must copy parameters to the first driver
  2859                              <1> 
  2860                              <1> li1:
  2861                              <1>                 ; !!!! Allocate memory
  2862                              <1>                 ; !!!! Move data to disk
  2863                              <1>                 mov dx,offset errs_load_fail
  2864                              <1>                 prints
  2865                              <1>                 ret
  2866                              <1> load_image      endp
  2867                              <1> 
  2868                              <1> errs_load_fail  db 'RAMDisk: Loaded disk image', 0Dh, 0Ah, '$'
  2869                              <1> s_image_loaded  db 'RAMDisk: Loaded disk image', 0Dh, 0Ah, '$'
  2870                              <1> 
  2871                              <1> %endif
  2872                              <1> 
  2873                              <1> ;**************************************************************************
  2874                              <1> ;
  2875                              <1> ;                       Initialization time data
  2876                              <1> ;
  2877                              <1> ;**************************************************************************
  2878                              <1> 
  2879                              <1> %if METHOD EQ 1
  2880                              <1> errs_noXMS      db 'RAMDisk: Extended Memory Manager not present.'
  2881                              <1>                 db 0Dh, 0Ah, '$'
  2882                              <1> 
  2883                              <1> errs_badXMS     db 'RAMDisk: Invalid XMS version. XMS 2.0 or above needed.'
  2884                              <1>                 db 0Dh, 0Ah, '$'
  2885                              <1> %endif
  2886                              <1> 
  2887                              <1> %if METHOD EQ 2
     0 000007DF 454D4D5858585830        EMM_name        db 'EMMXXXX0'
  2889                              <1> 
     0 000007E7 52414D4469736B3A20      errs_noEMS      db 'RAMDisk: Expanded Memory Manager not present.'
     0 000007F0 457870616E64656420
     0 000007F9 4D656D6F7279204D61
     0 00000802 6E61676572206E6F74
     0 0000080B 2070726573656E742E
     0 00000814 0D0A24                                  db 0Dh, 0Ah, '$'
  2892                              <1> 
     0 00000817 52414D4469736B3A20      errs_badEMS     db 'RAMDisk: Invalid EMS version. EMS 4.0 needed.'
     0 00000820 496E76616C69642045
     0 00000829 4D532076657273696F
     0 00000832 6E2E20454D5320342E
     0 0000083B 30206E65656465642E
     0 00000844 0D0A24                                  db 0Dh, 0Ah, '$'
  2895                              <1> 
     0 00000847 52414D4469736B3A20      errs_nofuncEMS  db 'RAMDisk: EMS driver does not support needed functions'
     0 00000850 454D53206472697665
     0 00000859 7220646F6573206E6F
     0 00000862 7420737570706F7274
     0 0000086B 206E65656465642066
     0 00000874 756E6374696F6E73
     0 0000087C 206F72206E6F206D65                      db ' or no memory available.'
     0 00000885 6D6F72792061766169
     0 0000088E 6C61626C652E
     0 00000894 0D0A24                                  db 0Dh, 0Ah, '$'
  2899                              <1> %endif
  2900                              <1> 
  2901                              <1> %if METHOD EQ 3
  2902                              <1> EMM_name        db 'EMMXXXX0'
  2903                              <1> 
  2904                              <1> errs_noEMS      db 'RAMDisk: Expanded Memory Manager not present.'
  2905                              <1>                 db 0Dh, 0Ah, '$'
  2906                              <1> 
  2907                              <1> errs_badEMS     db 'RAMDisk: Invalid EMS version. EMS 4.0 needed.'
  2908                              <1>                 db 0Dh, 0Ah, '$'
  2909                              <1> 
  2910                              <1> errs_nofuncEMS  db 'RAMDisk: EMS driver does not support needed functions'
  2911                              <1>                 db ' or no memory available.'
  2912                              <1>                 db 0Dh, 0Ah, '$'
  2913                              <1> %endif
  2914                              <1> 
  2915                              <1> ;**************************************************************************
  2916                              <1> ;
  2917                              <1> ;                       Initialization strings
  2918                              <1> ;
  2919                              <1> ;**************************************************************************
  2920                              <1> 
     0 00000897 52414D4469736B3A20      errs_eDOS       db 'RAMDisk: Incorrect DOS version.'
     0 000008A0 496E636F7272656374
     0 000008A9 20444F532076657273
     0 000008B2 696F6E2E
     0 000008B6 0D0A24                                  db 0Dh, 0Ah, '$'
  2923                              <1> 
     0 000008B9 52414D4469736B3A20      errs_i2D_invalid:	ascic "RAMDisk: Multiplex interrupt 2Dh invalid.",13,10
     0 000008C2 4D756C7469706C6578
     0 000008CB 20696E746572727570
     0 000008D4 742032446820696E76
     0 000008DD 616C69642E0D0A24
  2925                              <1> 
     0 000008E5 52414D4469736B3A20      errs_i2D_no_free:	ascic "RAMDisk: No free int 2Dh multiplex number.",13,10
     0 000008EE 4E6F20667265652069
     0 000008F7 6E7420324468206D75
     0 00000900 6C7469706C6578206E
     0 00000909 756D6265722E0D0A24
  2927                              <1> 
     0 00000912 52414D4469736B3A20      errs_ml_version db 'RAMDisk: Driver of different version already '
     0 0000091B 447269766572206F66
     0 00000924 20646966666572656E
     0 0000092D 742076657273696F6E
     0 00000936 20616C726561647920
     0 0000093F 696E7374616C6C6564                      db 'installed.'
     0 00000948 2E
     0 00000949 0D0A24                                  db 0Dh, 0Ah, '$'
  2931                              <1> 
     0 0000094C 52414D4469736B3A20      errs_noappend   db 'RAMDisk: Can not append to previously installed driver.'
     0 00000955 43616E206E6F742061
     0 0000095E 7070656E6420746F20
     0 00000967 70726576696F75736C
     0 00000970 7920696E7374616C6C
     0 00000979 656420647269766572
     0 00000982 2E
     0 00000983 0D0A24                                  db 0Dh, 0Ah, '$'
  2934                              <1> 
     0 00000986 52414D4469736B3A20      errs_syntax     db 'RAMDisk: Syntax error', 0Dh, 0Ah, 0Dh, 0Ah
     0 0000098F 53796E746178206572
     0 00000998 726F720D0A0D0A
     0 0000099F 53796E7461783A2053                      db 'Syntax: SRDISK.SYS [d:] [/A] [/MPX=hh]', 0Dh, 0Ah, 0Dh, 0Ah
     0 000009A8 524449534B2E535953
     0 000009B1 205B643A5D205B2F41
     0 000009BA 5D205B2F4D50583D68
     0 000009C3 685D0D0A0D0A
     0 000009C9 20643A094472697665                      db ' d:', 9, 'Drive into which to append or the drive letter'
     0 000009D2 20696E746F20776869
     0 000009DB 636820746F20617070
     0 000009E4 656E64206F72207468
     0 000009ED 65206472697665206C
     0 000009F6 6574746572
     0 000009FB 0D0A                                    db 0Dh, 0Ah
     0 000009FD 096F66207468697320                      db 9, 'of this device if DOS does not report it to it '
     0 00000A06 646576696365206966
     0 00000A0F 20444F5320646F6573
     0 00000A18 206E6F74207265706F
     0 00000A21 727420697420746F20
     0 00000A2A 697420
     0 00000A2D 636F72726563746C79                      db 'correctly.'
     0 00000A36 2E
     0 00000A37 0D0A                                    db 0Dh, 0Ah
     0 00000A39 202F4109417070656E                      db ' /A', 9, 'Append this driver to previous SRDISK '
     0 00000A42 642074686973206472
     0 00000A4B 6976657220746F2070
     0 00000A54 726576696F75732053
     0 00000A5D 524449534B20
     0 00000A63 6472697665722E                          db 'driver.'
     0 00000A6A 0D0A                                    db 0Dh, 0Ah
     0 00000A6C 202F4D50583D095365                      db " /MPX=",9,"Set multiplex number (hexadecimal) to try first."
     0 00000A75 74206D756C7469706C
     0 00000A7E 6578206E756D626572
     0 00000A87 202868657861646563
     0 00000A90 696D616C2920746F20
     0 00000A99 747279206669727374
     0 00000AA2 2E
     0 00000AA3 0D0A24                                  db 0Dh, 0Ah, '$'
  2947                              <1> 
     0 00000AA6 0D0A526553697A6561      s_sign_on       db 0Dh, 0Ah, 'ReSizeable RAMDisk '
     0 00000AAF 626C652052414D4469
     0 00000AB8 736B20
     0 00000ABB 28454D5329                              db '(', MEMORY_STR, ')'
     0 00000AC0 2076657273696F6E20                      db ' version ', SRD_VERSION, '. '	; NASM port swapped text literals
     0 00000AC9 322E31302E20
     0 00000ACF 436F70797269676874                      db 'Copyright (c) 2005 Marko Kohtala.'
     0 00000AD8 202863292032303035
     0 00000AE1 204D61726B6F204B6F
     0 00000AEA 6874616C612E
     0 00000AF0 0D0A24                                  db 0Dh, 0Ah, '$'
  2953                              <1> 
     0 00000AF3 496E7374616C6C6564      s_installed     db 'Installed RAMDrive '
     0 00000AFC 2052414D4472697665
     0 00000B05 20
     0 00000B06 433A206F6E206D756C      s_drive         db "C: on multiplex ",36
     0 00000B0F 7469706C65782024
  2956                              <1>   
     0 00000B17 417070656E64656420      s_appended      db 'Appended to RAMDrive '
     0 00000B20 746F2052414D447269
     0 00000B29 766520
     0 00000B2C 433A206F6E206D756C      s_appdrive      db "C: on multiplex ",36
     0 00000B35 7469706C65782024
  2959                              <1> 
     0 00000B3D 680D0A24                s_end:		db "h",13,10,36
  2961                              <1> 
  2962                              <1> 
  2963                              <1> ;**************************************************************************
  2964                              <1> ;
  2965                              <1> ;                       A note for binary debuggers
  2966                              <1> ;
  2967                              <1> ;**************************************************************************
  2968                              <1> 
     0 00000B41 0D0A436F7079726967      db 0Dh, 0Ah, "Copyright (C) 1992-1996,2005 Marko Kohtala. "
     0 00000B4A 687420284329203139
     0 00000B53 39322D313939362C32
     0 00000B5C 303035204D61726B6F
     0 00000B65 204B6F6874616C612E
     0 00000B6E 20
     0 00000B6F 0D0A436F6E74616374      db 0Dh, 0Ah, "Contact at 'kohtala@users.sourceforge.net'."
     0 00000B78 20617420276B6F6874
     0 00000B81 616C61407573657273
     0 00000B8A 2E736F75726365666F
     0 00000B93 7267652E6E6574272E
     0 00000B9C 0D0A                    db 0Dh, 0Ah
  2972                              <1> 
  2973                              <1> ; (no prior section) ; d_seg           ends
  2974                              <1>                 end
  2975                              <1> 
  2976                              <1> %ifidni __OUTPUT_FORMAT__, obj
=== Switch to base=000BA0h -> "STACK"
  2977                              <1> section STACK stack
  2978 00000000 <res 200h>          <1> 	resb 512			; to silence linker warning
  2979                              <1> %endif
    29                                  ;=== Pop trace listing source
